From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.remote-ip=192.198.163.13 ARC-Seal: i=1; d=subspace.kernel.org; s=arc20261015; a=rsa-sha256; cv=none; t=1794291424; b=DBeLwmWsU/GyadFMhNwN/X2WTj60qqfl1epgP9pxuM2og6AKRKSb4BlWFqbPFdayskk2 tsOEWZFnE4TBkaDK7LxsNXZkICmMP7j3orCpwraulzQT2c9CYynmQaEtXPqljDGKerfBh lgci6nTqJbziknfHzuF4M0fIfkmuEEktiZU3JPZy11qYPRynZ+cB4SvjuczEnDs1YiuLR dqNdDTCP83OQWntFTxNsvDJn7Op17cgqchSW1k0ZPN38swenuWtUeE0rfPysDCZdP/IkV z9RlAJIxqxw3BVg6T5dYnUlsEginF858WuwVynwvxfpDP2S1wMwha2cn7Wypt+yEYCA== ARC-Message-Signature: i=1; d=subspace.kernel.org; s=arc20261015; a=rsa-sha256; c=relaxed/relaxed; t=1794291424; h=DMARC-Filter:DKIM-Signature:X-CSE-ConnectionGUID:X-CSE-MsgGUID: X-IronPort-AV:X-IronPort-AV:Received:X-CSE-ConnectionGUID: X-CSE-MsgGUID:X-ExtLoop1:X-IronPort-AV:Received:From:To:Cc:Subject: Date:Message-Id:X-Mailer:In-Reply-To:References:MIME-Version: Content-Transfer-Encoding; bh=xeFPbdsgCvfdilI3hnNFnxsaQNSj3jvgh8ks8CrZWk8=; b=4PUlD6wMjXGpUw8i5+qRy0hKtmciVlFsif2t5I/Nj2hkHzzJy6esin01nTbsWz2BGLur 06biz2SO7gBQmoYxOvEZFTb7wPiK2fLMhWOPknWtXNj+8zLOIV7Xn6dY5crX+QlgN4aH7 y7lXZgtm0eovg08W5zpsQgRCIz1in+kzADeFrBNlcQBusBqtgFz2BGrJOzPRC4VueuJkY he+KvIIWy8JyHFawtkBiTpbN+TJCOSTVK+lQxXVFpdMV1aHYXroLk2+BPsWvEPcq7/gjn 8UIH4xSkLHxfD2ajk6a07+wXgMh9H3dqAgGaLFAwtW3maFcos02xn77AqdI9kxLS4mQ== ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass header.from=intel.com; spf=pass smtp.mailfrom=intel.com; dkim=pass header.d=intel.com header.i=@intel.com header.a=rsa-sha256 header.s=Intel header.b=hv8NWW2l; arc=none smtp.remote-ip=192.198.163.13 Received: from mgamail.intel.com (mgamail.intel.com [192.198.163.13]) (using TLSv1.2 with cipher ECDHE-ECDSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id C2D5A606A31C; Tue, 10 Nov 2026 06:17:02 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.4.2 smtp.subspace.kernel.org C2D5A606A31C Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=intel.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=intel.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=intel.com header.i=@intel.com header.a=rsa-sha256 header.s=Intel header.b=hv8NWW2l DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1794291422; x=1825827422; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=U02QbaXoTP8IpovVgpNBPyZTykshKNBqnPjxliRwFkM=; b=hv8NWW2lRIEMn6pP/xu50EarC5exNJAq/FRyyVEeA7zdoGgG7+CBjuHI khSZpWT1dI3JIzhYpxU8WiEzwJJbGsivEfCNXlQyTVkKspytNvhurFwTm ayg6OD/mO6WipmukLx234EH3NUBFQopWaZjSuseaVu+pymETQ+xvpzACv LJXz6TL9HaBpSHO3maPfUQJ5lVpoKZ0+BsUCDg4tCztPkP/Bbxc6XfTgV wDdx1t6S79dkMdn6/TG0pe2VKKihD3yTtjfy7U9juBUNmJtNDQnHTD/Kv A/QJMLospBiidhKPTGTnFflMIQhzY5j+awVuqhhH4nN5y/AJV3BU5dUtj A==; X-CSE-ConnectionGUID: pwoL/C5sTzKwN6p5rE66Qg== X-CSE-MsgGUID: OJr2HfAYTeGbovEySzsfKQ== X-IronPort-AV: E=McAfee;i="6800,10657,11961"; a="3020916" X-IronPort-AV: E=Sophos;i="6.27,205,1787036400"; d="scan'208";a="3020916" Received: from orviesa004.jf.intel.com ([10.64.159.144]) by fmvoesa107.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 09 Nov 2026 22:17:02 -0800 X-CSE-ConnectionGUID: chMDQ6LJR62nkPDnvk9UZw== X-CSE-MsgGUID: +n2EgzFkRsG0PqsjEd8M5g== X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="6.27,205,1787036400"; d="scan'208";a="7930947" Received: from kandpal-x299-ud4-pro.iind.intel.com ([10.190.239.10]) by orviesa004.jf.intel.com with ESMTP; 09 Nov 2026 22:16:56 -0800 From: Suraj Kandpal To: dri-devel@lists.freedesktop.org, amd-gfx@lists.freedesktop.org, freedreno@lists.freedesktop.org, linux-arm-msm@vger.kernel.org, linux-renesas-soc@vger.kernel.org, intel-gfx@lists.freedesktop.org, intel-xe@lists.freedesktop.org, linux-kernel@vger.kernel.org Cc: dmitry.baryshkov@oss.qualcomm.com, John.Harrison@Igalia.com, kernel-dev@igalia.com, alex.hung@amd.com, liviu.dudau@arm.com, louis.chauvet@bootlin.com, maarten.lankhorst@linux.intel.com, mripard@kernel.org, tzimmermann@suse.de, airlied@gmail.com, simona@ffwll.ch, laurent.pinchart+renesas@ideasonboard.com, tomi.valkeinen+renesas@ideasonboard.com, kieran.bingham+renesas@ideasonboard.com, dave.stevenson@raspberrypi.com, mcanal@igalia.com, kernel-list@raspberrypi.com, uma.shankar@intel.com, arun.r.murthy@intel.com Subject: [PATCH v7 DO NOT REVIEW 1/8] drm: writeback: drop excess connector initialization functions Date: Tue, 10 Nov 2026 11:46:30 +0530 Message-Id: <20261110061637.2500929-2-suraj.kandpal@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20261110061637.2500929-1-suraj.kandpal@intel.com> References: <20261110061637.2500929-1-suraj.kandpal@intel.com> X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Post: List-Help: List-Subscribe: List-Unsubscribe: List-Owner: Precedence: list MIME-Version: 1.0 Content-Transfer-Encoding: 8bit From: Dmitry Baryshkov Now as all drivers have been converted to drm_writeback_connector_init_with_encoder(), drop drm_writeback_connector_init() and drm_writeback_connector::encoder field, they are unused now. Signed-off-by: Dmitry Baryshkov --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h | 1 + .../drm/amd/display/amdgpu_dm/amdgpu_dm_wb.c | 27 +++- .../display/amdgpu_dm/tests/amdgpu_dm_test.c | 4 +- .../amdgpu_dm/tests/amdgpu_dm_wb_test.c | 4 +- .../gpu/drm/arm/display/komeda/komeda_kms.h | 3 + .../arm/display/komeda/komeda_wb_connector.c | 24 ++- drivers/gpu/drm/arm/malidp_drv.h | 1 + drivers/gpu/drm/arm/malidp_mw.c | 25 ++- drivers/gpu/drm/drm_connector.c | 3 + drivers/gpu/drm/drm_crtc_internal.h | 3 + drivers/gpu/drm/drm_writeback.c | 147 ++++-------------- .../gpu/drm/renesas/rcar-du/rcar_du_crtc.h | 2 + .../drm/renesas/rcar-du/rcar_du_writeback.c | 29 +++- drivers/gpu/drm/vc4/vc4_txp.c | 8 +- include/drm/drm_writeback.h | 22 +-- 16 files changed, 140 insertions(+), 165 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 94d45e5d2a3b..12bc10f852e2 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -4830,7 +4830,7 @@ dm_set_writeback(struct amdgpu_display_manager *dm, goto cleanup; } - acrtc = to_amdgpu_crtc(wb_conn->encoder.crtc); + acrtc = to_amdgpu_crtc(to_amdgpu_dm_wb_connector(wb_conn)->encoder.crtc); if (!acrtc) { drm_err(adev_to_drm(adev), "no amdgpu_crtc found\n"); goto cleanup; diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h index 6cd3f04e7701..aa838a9367d8 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h @@ -946,6 +946,7 @@ static inline void amdgpu_dm_set_mst_status(uint8_t *status, struct amdgpu_dm_wb_connector { struct drm_writeback_connector base; + struct drm_encoder encoder; struct dc_link *link; }; diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_wb.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_wb.c index 39b7b3e49f6b..dde02b2b018b 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_wb.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_wb.c @@ -218,6 +218,10 @@ STATIC_IFN_KUNIT void amdgpu_dm_wb_cleanup_job(struct drm_writeback_connector *c } EXPORT_IF_KUNIT(amdgpu_dm_wb_cleanup_job); +static const struct drm_encoder_funcs amdgpu_dm_wb_encoder_funcs = { + .destroy = drm_encoder_cleanup, +}; + static const struct drm_encoder_helper_funcs amdgpu_dm_wb_encoder_helper_funcs = { .atomic_check = amdgpu_dm_wb_encoder_atomic_check, }; @@ -247,17 +251,26 @@ int amdgpu_dm_wb_connector_init(struct amdgpu_display_manager *dm, wbcon->link = link; + drm_encoder_helper_add(&wbcon->encoder, &amdgpu_dm_wb_encoder_helper_funcs); + wbcon->encoder.possible_crtcs = amdgpu_dm_get_encoder_crtc_mask(dm->adev); + + res = drm_encoder_init(&dm->adev->ddev, &wbcon->encoder, + &amdgpu_dm_wb_encoder_funcs, + DRM_MODE_ENCODER_VIRTUAL, NULL); + if (res) + return res; + drm_connector_helper_add(&wbcon->base.base, &amdgpu_dm_wb_conn_helper_funcs); res = drm_writeback_connector_init(&dm->adev->ddev, &wbcon->base, - &amdgpu_dm_wb_connector_funcs, - &amdgpu_dm_wb_encoder_helper_funcs, - amdgpu_dm_wb_formats, - ARRAY_SIZE(amdgpu_dm_wb_formats), - amdgpu_dm_get_encoder_crtc_mask(dm->adev)); - - if (res) + &amdgpu_dm_wb_connector_funcs, + &wbcon->encoder, + amdgpu_dm_wb_formats, + ARRAY_SIZE(amdgpu_dm_wb_formats)); + if (res) { + drm_encoder_cleanup(&wbcon->encoder); return res; + } /* * Some of the properties below require access to state, like bpc. * Allocate some default initial connector state with our reset helper. diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_test.c b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_test.c index c375ee68778b..61b72eba4c31 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_test.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_test.c @@ -4567,7 +4567,7 @@ static void dm_test_clear_writeback_removes_stream(struct kunit *test) static void dm_test_set_writeback_no_pipe(struct kunit *test) { struct amdgpu_device *adev = dm_kunit_alloc_adev(test); - struct drm_writeback_connector *wb_conn; + struct amdgpu_dm_wb_connector *wb_conn; struct drm_connector_state *conn_state; struct drm_writeback_job *job; struct amdgpu_framebuffer *afb; @@ -4597,7 +4597,7 @@ static void dm_test_set_writeback_no_pipe(struct kunit *test) conn_state->writeback_job = job; crtc_state->stream = dm_kunit_alloc_stream(test, NULL); - dm_set_writeback(&adev->dm, crtc_state, &wb_conn->base, conn_state); + dm_set_writeback(&adev->dm, crtc_state, &wb_conn->base.base, conn_state); KUNIT_EXPECT_NULL(test, acrtc->wb_conn); KUNIT_EXPECT_FALSE(test, acrtc->wb_pending); diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_wb_test.c b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_wb_test.c index 914d41290977..8ba4299578ea 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_wb_test.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/amdgpu_dm_wb_test.c @@ -511,8 +511,8 @@ static void dm_test_wb_connector_init_success(struct kunit *test) KUNIT_EXPECT_TRUE(test, wbcon->base.base.funcs != NULL); KUNIT_EXPECT_TRUE(test, wbcon->base.base.helper_private != NULL); KUNIT_EXPECT_TRUE(test, wbcon->base.base.state != NULL); - KUNIT_EXPECT_TRUE(test, wbcon->base.encoder.funcs != NULL); - KUNIT_EXPECT_EQ(test, wbcon->base.encoder.possible_crtcs, 0x1); + KUNIT_EXPECT_TRUE(test, wbcon->encoder.funcs != NULL); + KUNIT_EXPECT_EQ(test, wbcon->encoder.possible_crtcs, 0x1); } /* Tests for amdgpu_dm_wb_prepare_job / amdgpu_dm_wb_cleanup_job */ diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_kms.h b/drivers/gpu/drm/arm/display/komeda/komeda_kms.h index 83e61c4080c2..4d41681a834b 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_kms.h +++ b/drivers/gpu/drm/arm/display/komeda/komeda_kms.h @@ -56,6 +56,9 @@ struct komeda_wb_connector { /** @base: &drm_writeback_connector */ struct drm_writeback_connector base; + /** @encoder: writeback encoder */ + struct drm_encoder encoder; + /** @wb_layer: represents associated writeback pipeline of komeda */ struct komeda_layer *wb_layer; }; diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_wb_connector.c b/drivers/gpu/drm/arm/display/komeda/komeda_wb_connector.c index f394971c0edb..ea4589b00ee0 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_wb_connector.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_wb_connector.c @@ -127,6 +127,10 @@ static void komeda_wb_connector_destroy(struct drm_connector *connector) kfree(to_kconn(to_wb_conn(connector))); } +static const struct drm_encoder_funcs komeda_wb_encoder_funcs = { + .destroy = drm_encoder_cleanup, +}; + static const struct drm_connector_funcs komeda_wb_connector_funcs = { .atomic_create_state = drm_atomic_helper_connector_create_state, .detect = komeda_wb_connector_detect, @@ -170,19 +174,29 @@ static int komeda_wb_connector_add(struct komeda_kms_dev *kms, return -ENOMEM; } + wb_encoder = &kwb_conn->encoder; + drm_encoder_helper_add(wb_encoder, &komeda_wb_encoder_helper_funcs); + wb_encoder->possible_crtcs = crtc_mask; + + err = drm_encoder_init(&kms->base, wb_encoder, &komeda_wb_encoder_funcs, + DRM_MODE_ENCODER_VIRTUAL, NULL); + if (err) { + komeda_put_fourcc_list(formats); + kfree(kwb_conn); + return err; + } + err = drm_writeback_connector_init(&kms->base, wb_conn, &komeda_wb_connector_funcs, - &komeda_wb_encoder_helper_funcs, - formats, n_formats, - BIT(drm_crtc_index(&kcrtc->base))); + wb_encoder, + formats, n_formats); komeda_put_fourcc_list(formats); if (err) { + drm_encoder_cleanup(wb_encoder); kfree(kwb_conn); return err; } - wb_encoder = &wb_conn->encoder; - /* * The writeback connector is associated with a single CRTC. Make its * encoder clone-compatible only with encoders that can drive that CRTC. diff --git a/drivers/gpu/drm/arm/malidp_drv.h b/drivers/gpu/drm/arm/malidp_drv.h index bc0387876dea..64610f2d23e2 100644 --- a/drivers/gpu/drm/arm/malidp_drv.h +++ b/drivers/gpu/drm/arm/malidp_drv.h @@ -33,6 +33,7 @@ struct malidp_drm { struct malidp_hw_device *dev; struct drm_crtc crtc; struct drm_writeback_connector mw_connector; + struct drm_encoder mw_encoder; wait_queue_head_t wq; struct drm_pending_vblank_event *event; atomic_t config_valid; diff --git a/drivers/gpu/drm/arm/malidp_mw.c b/drivers/gpu/drm/arm/malidp_mw.c index 8d1e1e3a6deb..3669d10540bf 100644 --- a/drivers/gpu/drm/arm/malidp_mw.c +++ b/drivers/gpu/drm/arm/malidp_mw.c @@ -110,6 +110,10 @@ malidp_mw_connector_duplicate_state(struct drm_connector *connector) return &mw_state->base; } +static const struct drm_encoder_funcs malidp_mw_encoder_funcs = { + .destroy = drm_encoder_cleanup, +}; + static const struct drm_connector_funcs malidp_mw_connector_funcs = { .atomic_create_state = malidp_mw_connector_create_state, .detect = malidp_mw_connector_detect, @@ -223,14 +227,27 @@ int malidp_mw_connector_init(struct drm_device *drm) if (!formats) return -ENOMEM; + drm_encoder_helper_add(&malidp->mw_encoder, + &malidp_mw_encoder_helper_funcs); + malidp->mw_encoder.possible_crtcs = drm_crtc_mask(&malidp->crtc); + + ret = drm_encoder_init(drm, &malidp->mw_encoder, + &malidp_mw_encoder_funcs, + DRM_MODE_ENCODER_VIRTUAL, NULL); + if (ret) { + kfree(formats); + return ret; + } + ret = drm_writeback_connector_init(drm, &malidp->mw_connector, &malidp_mw_connector_funcs, - &malidp_mw_encoder_helper_funcs, - formats, n_formats, - 1 << drm_crtc_index(&malidp->crtc)); + &malidp->mw_encoder, + formats, n_formats); kfree(formats); - if (ret) + if (ret) { + drm_encoder_cleanup(&malidp->mw_encoder); return ret; + } return 0; } diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index d66188521881..888bb1f78d2d 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -921,6 +921,9 @@ void drm_connector_cleanup(struct drm_connector *connector) if (connector->hdmi.scdc_work_initialized) cancel_delayed_work_sync(&connector->hdmi.scdc_work); + if (connector->connector_type == DRM_MODE_CONNECTOR_WRITEBACK) + drm_writeback_connector_cleanup(connector); + platform_device_unregister(connector->hdmi_audio.codec_pdev); if (connector->privacy_screen) { diff --git a/drivers/gpu/drm/drm_crtc_internal.h b/drivers/gpu/drm/drm_crtc_internal.h index 3492787c3697..f60216adcd31 100644 --- a/drivers/gpu/drm/drm_crtc_internal.h +++ b/drivers/gpu/drm/drm_crtc_internal.h @@ -329,4 +329,7 @@ static inline void drm_panic_unregister(struct drm_device *dev) {} static inline void drm_panic_init(void) {} #endif +/* drm_writeback.c */ +void drm_writeback_connector_cleanup(struct drm_connector *connector); + #endif /* __DRM_CRTC_INTERNAL_H__ */ diff --git a/drivers/gpu/drm/drm_writeback.c b/drivers/gpu/drm/drm_writeback.c index b4a002e6d043..0c5d2fbe7a7c 100644 --- a/drivers/gpu/drm/drm_writeback.c +++ b/drivers/gpu/drm/drm_writeback.c @@ -16,11 +16,12 @@ #include #include #include -#include #include #include #include +#include "drm_crtc_internal.h" + /** * DOC: overview * @@ -148,80 +149,8 @@ static int create_writeback_properties(struct drm_device *dev) return 0; } -static const struct drm_encoder_funcs drm_writeback_encoder_funcs = { - .destroy = drm_encoder_cleanup, -}; - /** - * drm_writeback_connector_init - Initialize a writeback connector and its properties - * @dev: DRM device - * @wb_connector: Writeback connector to initialize - * @con_funcs: Connector funcs vtable - * @enc_helper_funcs: Encoder helper funcs vtable to be used by the internal encoder - * @formats: Array of supported pixel formats for the writeback engine - * @n_formats: Length of the formats array - * @possible_crtcs: possible crtcs for the internal writeback encoder - * - * This function creates the writeback-connector-specific properties if they - * have not been already created, initializes the connector as - * type DRM_MODE_CONNECTOR_WRITEBACK, and correctly initializes the property - * values. It will also create an internal encoder associated with the - * drm_writeback_connector and set it to use the @enc_helper_funcs vtable for - * the encoder helper. - * - * Drivers should always use this function instead of drm_connector_init() to - * set up writeback connectors. - * - * Returns: 0 on success, or a negative error code - */ -int drm_writeback_connector_init(struct drm_device *dev, - struct drm_writeback_connector *wb_connector, - const struct drm_connector_funcs *con_funcs, - const struct drm_encoder_helper_funcs *enc_helper_funcs, - const u32 *formats, int n_formats, - u32 possible_crtcs) -{ - int ret = 0; - - drm_encoder_helper_add(&wb_connector->encoder, enc_helper_funcs); - - wb_connector->encoder.possible_crtcs = possible_crtcs; - - ret = drm_encoder_init(dev, &wb_connector->encoder, - &drm_writeback_encoder_funcs, - DRM_MODE_ENCODER_VIRTUAL, NULL); - if (ret) - return ret; - - ret = drm_writeback_connector_init_with_encoder(dev, wb_connector, &wb_connector->encoder, - con_funcs, formats, n_formats); - - if (ret) - drm_encoder_cleanup(&wb_connector->encoder); - - return ret; -} -EXPORT_SYMBOL(drm_writeback_connector_init); - -static void delete_writeback_properties(struct drm_device *dev) -{ - if (dev->mode_config.writeback_pixel_formats_property) { - drm_property_destroy(dev, dev->mode_config.writeback_pixel_formats_property); - dev->mode_config.writeback_pixel_formats_property = NULL; - } - if (dev->mode_config.writeback_out_fence_ptr_property) { - drm_property_destroy(dev, dev->mode_config.writeback_out_fence_ptr_property); - dev->mode_config.writeback_out_fence_ptr_property = NULL; - } - if (dev->mode_config.writeback_fb_id_property) { - drm_property_destroy(dev, dev->mode_config.writeback_fb_id_property); - dev->mode_config.writeback_fb_id_property = NULL; - } -} - -/** - * __drm_writeback_connector_init - Initialize a writeback connector with - * a custom encoder + * __drm_writeback_connector_init - Initialize a writeback connector * * @dev: DRM device * @wb_connector: Writeback connector to initialize @@ -254,20 +183,18 @@ static int __drm_writeback_connector_init(struct drm_device *dev, int ret = create_writeback_properties(dev); if (ret != 0) - goto failed_properties; + return ret; connector->interlace_allowed = 0; ret = drm_connector_attach_encoder(connector, enc); if (ret) - goto failed_properties; + return ret; blob = drm_property_create_blob(dev, n_formats * sizeof(*formats), formats); - if (IS_ERR(blob)) { - ret = PTR_ERR(blob); - goto failed_properties; - } + if (IS_ERR(blob)) + return PTR_ERR(blob); INIT_LIST_HEAD(&wb_connector->job_queue); spin_lock_init(&wb_connector->job_lock); @@ -290,14 +217,10 @@ static int __drm_writeback_connector_init(struct drm_device *dev, wb_connector->pixel_formats_blob_ptr = blob; return 0; -failed_properties: - delete_writeback_properties(dev); - return ret; } /** - * drm_writeback_connector_init_with_encoder - Initialize a writeback connector with - * a custom encoder + * drm_writeback_connector_init - Initialize a writeback connector * * @dev: DRM device * @wb_connector: Writeback connector to initialize @@ -324,11 +247,11 @@ static int __drm_writeback_connector_init(struct drm_device *dev, * * Returns: 0 on success, or a negative error code */ -int drm_writeback_connector_init_with_encoder(struct drm_device *dev, - struct drm_writeback_connector *wb_connector, - struct drm_encoder *enc, - const struct drm_connector_funcs *con_funcs, - const u32 *formats, int n_formats) +int drm_writeback_connector_init(struct drm_device *dev, + struct drm_writeback_connector *wb_connector, + const struct drm_connector_funcs *con_funcs, + struct drm_encoder *enc, + const u32 *formats, int n_formats) { struct drm_connector *connector = &wb_connector->base; int ret; @@ -345,26 +268,31 @@ int drm_writeback_connector_init_with_encoder(struct drm_device *dev, return ret; } -EXPORT_SYMBOL(drm_writeback_connector_init_with_encoder); +EXPORT_SYMBOL(drm_writeback_connector_init); /** * drm_writeback_connector_cleanup - Cleanup the writeback connector - * @dev: DRM device - * @data: Pointer to the writeback connector to clean up + * @connector: Writeback connector to clean up * - * This will decrement the reference counter of blobs and destroy properties. It - * will also clean the remaining jobs in this writeback connector. Caution: This helper will not + * This will decrement the reference counter of blobs. It will also clean the + * remaining jobs in this writeback connector. Caution: This helper will not * clean up the attached encoder and the drm_connector. + * + * Called from drm_connector_cleanup() for all writeback connectors. */ -static void drm_writeback_connector_cleanup(struct drm_device *dev, - void *data) +void drm_writeback_connector_cleanup(struct drm_connector *connector) { - unsigned long flags; + struct drm_writeback_connector *wb_connector = + drm_connector_to_writeback(connector); struct drm_writeback_job *pos, *n; - struct drm_writeback_connector *wb_connector = data; + unsigned long flags; + + /* __drm_writeback_connector_init() has failed */ + if (!wb_connector->pixel_formats_blob_ptr) + return; - delete_writeback_properties(dev); drm_property_blob_put(wb_connector->pixel_formats_blob_ptr); + wb_connector->pixel_formats_blob_ptr = NULL; spin_lock_irqsave(&wb_connector->job_lock, flags); list_for_each_entry_safe(pos, n, &wb_connector->job_queue, list_entry) { @@ -375,8 +303,7 @@ static void drm_writeback_connector_cleanup(struct drm_device *dev, } /** - * drmm_writeback_connector_init - Initialize a writeback connector with - * a custom encoder + * drmm_writeback_connector_init - Initialize a writeback connector * * @dev: DRM device * @wb_connector: Writeback connector to initialize @@ -385,7 +312,8 @@ static void drm_writeback_connector_cleanup(struct drm_device *dev, * @formats: Array of supported pixel formats for the writeback engine * @n_formats: Length of the formats array * - * This function initialize a writeback connector and register its cleanup. + * This function initializes a writeback connector. Cleanup is automatically + * handled with a call to drm_connector_cleanup() in a DRM-managed action. * * This function creates the writeback-connector-specific properties if they * have not been already created, initializes the connector as @@ -408,17 +336,8 @@ int drmm_writeback_connector_init(struct drm_device *dev, if (ret) return ret; - ret = __drm_writeback_connector_init(dev, wb_connector, enc, formats, - n_formats); - if (ret) - return ret; - - ret = drmm_add_action_or_reset(dev, drm_writeback_connector_cleanup, - wb_connector); - if (ret) - return ret; - - return 0; + return __drm_writeback_connector_init(dev, wb_connector, enc, formats, + n_formats); } EXPORT_SYMBOL(drmm_writeback_connector_init); diff --git a/drivers/gpu/drm/renesas/rcar-du/rcar_du_crtc.h b/drivers/gpu/drm/renesas/rcar-du/rcar_du_crtc.h index 8857926e109a..d8b1dcab8dea 100644 --- a/drivers/gpu/drm/renesas/rcar-du/rcar_du_crtc.h +++ b/drivers/gpu/drm/renesas/rcar-du/rcar_du_crtc.h @@ -44,6 +44,7 @@ struct rcar_du_vsp; * @vsp: VSP feeding video to this CRTC * @vsp_pipe: index of the VSP pipeline feeding video to this CRTC * @writeback: the writeback connector + * @encoder: the writeback encoder */ struct rcar_du_crtc { struct drm_crtc crtc; @@ -74,6 +75,7 @@ struct rcar_du_crtc { unsigned int sources_count; struct drm_writeback_connector writeback; + struct drm_encoder encoder; }; #define to_rcar_crtc(c) container_of(c, struct rcar_du_crtc, crtc) diff --git a/drivers/gpu/drm/renesas/rcar-du/rcar_du_writeback.c b/drivers/gpu/drm/renesas/rcar-du/rcar_du_writeback.c index 0a3108965591..a88408124758 100644 --- a/drivers/gpu/drm/renesas/rcar-du/rcar_du_writeback.c +++ b/drivers/gpu/drm/renesas/rcar-du/rcar_du_writeback.c @@ -172,6 +172,10 @@ static int rcar_du_wb_enc_atomic_check(struct drm_encoder *encoder, return 0; } +static const struct drm_encoder_funcs rcar_du_wb_enc_funcs = { + .destroy = drm_encoder_cleanup, +}; + static const struct drm_encoder_helper_funcs rcar_du_wb_enc_helper_funcs = { .atomic_check = rcar_du_wb_enc_atomic_check, }; @@ -199,16 +203,29 @@ int rcar_du_writeback_init(struct rcar_du_device *rcdu, struct rcar_du_crtc *rcrtc) { struct drm_writeback_connector *wb_conn = &rcrtc->writeback; + struct drm_encoder *encoder = &rcrtc->encoder; + int ret; + + drm_encoder_helper_add(encoder, &rcar_du_wb_enc_helper_funcs); + encoder->possible_crtcs = drm_crtc_mask(&rcrtc->crtc); + + ret = drm_encoder_init(&rcdu->ddev, encoder, &rcar_du_wb_enc_funcs, + DRM_MODE_ENCODER_VIRTUAL, NULL); + if (ret) + return ret; drm_connector_helper_add(&wb_conn->base, &rcar_du_wb_conn_helper_funcs); - return drm_writeback_connector_init(&rcdu->ddev, wb_conn, - &rcar_du_wb_conn_funcs, - &rcar_du_wb_enc_helper_funcs, - writeback_formats, - ARRAY_SIZE(writeback_formats), - 1 << drm_crtc_index(&rcrtc->crtc)); + ret = drm_writeback_connector_init(&rcdu->ddev, wb_conn, + &rcar_du_wb_conn_funcs, + encoder, + writeback_formats, + ARRAY_SIZE(writeback_formats)); + if (ret) + drm_encoder_cleanup(encoder); + + return ret; } void rcar_du_writeback_setup(struct rcar_du_crtc *rcrtc, diff --git a/drivers/gpu/drm/vc4/vc4_txp.c b/drivers/gpu/drm/vc4/vc4_txp.c index 642953cba25f..6ffc54d23d48 100644 --- a/drivers/gpu/drm/vc4/vc4_txp.c +++ b/drivers/gpu/drm/vc4/vc4_txp.c @@ -601,10 +601,10 @@ static int vc4_txp_bind(struct device *dev, struct device *master, void *data) drm_connector_helper_add(&txp->connector.base, &vc4_txp_connector_helper_funcs); - ret = drm_writeback_connector_init_with_encoder(drm, &txp->connector, - encoder, - &vc4_txp_connector_funcs, - drm_fmts, ARRAY_SIZE(drm_fmts)); + ret = drm_writeback_connector_init(drm, &txp->connector, + &vc4_txp_connector_funcs, + encoder, + drm_fmts, ARRAY_SIZE(drm_fmts)); if (ret) return ret; diff --git a/include/drm/drm_writeback.h b/include/drm/drm_writeback.h index c380a7b8f55a..958466a05e60 100644 --- a/include/drm/drm_writeback.h +++ b/include/drm/drm_writeback.h @@ -24,17 +24,6 @@ struct drm_writeback_connector { */ struct drm_connector base; - /** - * @encoder: Internal encoder used by the connector to fulfill - * the DRM framework requirements. The users of the - * @drm_writeback_connector control the behaviour of the @encoder - * by passing the @enc_funcs parameter to drm_writeback_connector_init() - * function. - * For users of drm_writeback_connector_init_with_encoder(), this field - * is not valid as the encoder is managed within their drivers. - */ - struct drm_encoder encoder; - /** * @pixel_formats_blob_ptr: * @@ -151,15 +140,8 @@ drm_connector_to_writeback(struct drm_connector *connector) int drm_writeback_connector_init(struct drm_device *dev, struct drm_writeback_connector *wb_connector, const struct drm_connector_funcs *con_funcs, - const struct drm_encoder_helper_funcs *enc_helper_funcs, - const u32 *formats, int n_formats, - u32 possible_crtcs); - -int drm_writeback_connector_init_with_encoder(struct drm_device *dev, - struct drm_writeback_connector *wb_connector, - struct drm_encoder *enc, - const struct drm_connector_funcs *con_funcs, const u32 *formats, - int n_formats); + struct drm_encoder *enc, + const u32 *formats, int n_formats); int drmm_writeback_connector_init(struct drm_device *dev, struct drm_writeback_connector *wb_connector, -- 2.34.1