[PATCH] drm: Deal with rotation in drm_plane_helper_check_update()
From: Ville Syrjälädrm_plane_helper_check_update() needs to account for the plane rotation for correct clipping/scaling calculations. Do so. There was an earlier attempt [1] to add this into intel_check_primary_plane() but I requested that it'd be put into the helper instead. An updated patch never materialized AFAICS, so I went ahead and cooked one up myself. [1] https://patchwork.freedesktop.org/patch/65177/ Cc: Nabendu Maiti Signed-off-by: Ville Syrjälä --- drivers/gpu/drm/armada/armada_overlay.c | 1 + drivers/gpu/drm/drm_plane_helper.c | 28 ++-- drivers/gpu/drm/i915/intel_display.c| 2 ++ drivers/gpu/drm/rockchip/rockchip_drm_vop.c | 1 + include/drm/drm_plane_helper.h | 1 + 5 files changed, 23 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/armada/armada_overlay.c b/drivers/gpu/drm/armada/armada_overlay.c index 148e8a42b2c6..1ee707ef6b8d 100644 --- a/drivers/gpu/drm/armada/armada_overlay.c +++ b/drivers/gpu/drm/armada/armada_overlay.c @@ -121,6 +121,7 @@ armada_ovl_plane_update(struct drm_plane *plane, struct drm_crtc *crtc, int ret; ret = drm_plane_helper_check_update(plane, crtc, fb, , , , + BIT(DRM_ROTATE_0), 0, INT_MAX, true, false, ); if (ret) return ret; diff --git a/drivers/gpu/drm/drm_plane_helper.c b/drivers/gpu/drm/drm_plane_helper.c index 369d2898ff9e..0c12fa1a696f 100644 --- a/drivers/gpu/drm/drm_plane_helper.c +++ b/drivers/gpu/drm/drm_plane_helper.c @@ -115,6 +115,7 @@ static int get_connectors_for_crtc(struct drm_crtc *crtc, * @src: source coordinates in 16.16 fixed point * @dest: integer destination coordinates * @clip: integer clipping coordinates + * @rotation: plane rotation * @min_scale: minimum @src:@dest scaling factor in 16.16 fixed point * @max_scale: maximum @src:@dest scaling factor in 16.16 fixed point * @can_position: is it legal to position the plane such that it @@ -134,16 +135,17 @@ static int get_connectors_for_crtc(struct drm_crtc *crtc, * Zero if update appears valid, error code on failure */ int drm_plane_helper_check_update(struct drm_plane *plane, - struct drm_crtc *crtc, - struct drm_framebuffer *fb, - struct drm_rect *src, - struct drm_rect *dest, - const struct drm_rect *clip, - int min_scale, - int max_scale, - bool can_position, - bool can_update_disabled, - bool *visible) + struct drm_crtc *crtc, + struct drm_framebuffer *fb, + struct drm_rect *src, + struct drm_rect *dest, + const struct drm_rect *clip, + unsigned int rotation, + int min_scale, + int max_scale, + bool can_position, + bool can_update_disabled, + bool *visible) { int hscale, vscale; @@ -163,6 +165,8 @@ int drm_plane_helper_check_update(struct drm_plane *plane, return -EINVAL; } + drm_rect_rotate(src, fb->width << 16, fb->height << 16, rotation); + /* Check scaling */ hscale = drm_rect_calc_hscale(src, dest, min_scale, max_scale); vscale = drm_rect_calc_vscale(src, dest, min_scale, max_scale); @@ -174,6 +178,9 @@ int drm_plane_helper_check_update(struct drm_plane *plane, } *visible = drm_rect_clip_scaled(src, dest, clip, hscale, vscale); + + drm_rect_rotate_inv(src, fb->width << 16, fb->height << 16, rotation); + if (!*visible) /* * Plane isn't visible; some drivers can handle this @@ -265,6 +272,7 @@ int drm_primary_helper_update(struct drm_plane *plane, struct drm_crtc *crtc, ret = drm_plane_helper_check_update(plane, crtc, fb, , , , + BIT(DRM_ROTATE_0), DRM_PLANE_HELPER_NO_SCALING, DRM_PLANE_HELPER_NO_SCALING, false, false, ); diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index c4cd9c94faa6..a726c5e91220 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -14029,6 +14029,7 @@ intel_check_primary_plane(struct
[Bug 93548] Grid Autosport causes a hard system crash
https://bugs.freedesktop.org/show_bug.cgi?id=93548 --- Comment #4 from Krzysztof A. Sobiecki --- (In reply to Edwin Smith from comment #3) > I am pretty sure this is the bug with xpad that can cause hangs when using > force feedback. This was reported by Feral during development of XCOM and > was fixed for SteamOS by Pierre-Loup but the fix has not made it's way > upstream to the main linux kernel. Mine or Florians bug you are talking about? -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/57b734db/attachment.html>
DRM support in Android
Thank u all for ur response.Please clarify whether android graphics stack and android-x86 graphics stack is same or not.I did n't find information about android-x86 graphics stack.Please provide some help. Thanks and Regards, Vijay Kumar Prathipati. On Fri, Jan 15, 2016 at 3:54 PM, Daniel Vetter wrote: > On Fri, Jan 15, 2016 at 09:35:27AM +0800, Chih-Wei Huang wrote: > > 2016-01-09 16:37 GMT+08:00 vijay kumar : > > > Thanks Greg .You Helped me a lot. > > > > > > On Thu, Jan 7, 2016 at 10:52 PM, Greg Hackmann > wrote: > > >> > > >> On Tue, Jan 5, 2016 at 12:06 AM, vijay kumar > wrote: > > >>> > > >>> Hii all, > > >>> I want to know some information regarding DRI and DRM > > >>> support in android.Does Android uses DRI drivers in MESA for Direct > > >>> rendering. > > >> > > >> The vendor needs to supply an EGL implementation at a well-known path > > >> ( > https://android.googlesource.com/platform/frameworks/native/+/android-6.0.1_r5/opengl/libs/EGL/Loader.cpp#41 > ). > > >> This can be Mesa or a proprietary library. > > > > Android-x86 is the first open source project > > that brought Mesa/DRM to the Android platform. > > Refer to: > > > > http://sourceforge.net/p/android-x86/external_libdrm/ > > http://sourceforge.net/p/android-x86/external_mesa/ > > http://sourceforge.net/p/android-x86/external_drm_gralloc/ (Drm based > > gralloc HAL) > > > > It's glad to see drm_gralloc is now a part of > > AOSP marshmallow release. > > Google Pixel C is probably the first (and only?) one > > android product that uses it. > > > > We have a devel group working on that. > > If you are interesting, I can invite you to join. > > Fyi Google just opened up their drm_hwcomposer implementation. Open as in > actually open for patches! > > https://dev.chromium.org/android/contributing-to-drm_hwcomposer > > Cheers, Daniel > -- > Daniel Vetter > Software Engineer, Intel Corporation > http://blog.ffwll.ch > -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/0765ec69/attachment.html>
[RFC 26/29] dma-buf/fence: remove pointless fence_timeline_signal at destroy phase
On 15/01/2016 14:55, Gustavo Padovan wrote: > From: Gustavo Padovan > > All changes to timeline value come through the user via > fence_timeline_signal() calls. When fence_timeline_destroy() is called no > changes on timeline->value happens hence call fence_timeline_signal() with > no increment is pointless. > > Signed-off-by: Gustavo Padovan > --- > drivers/dma-buf/fence.c | 6 +- > 1 file changed, 1 insertion(+), 5 deletions(-) > > diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c > index 7a5fc9b..26f5f0f 100644 > --- a/drivers/dma-buf/fence.c > +++ b/drivers/dma-buf/fence.c > @@ -136,7 +136,7 @@ EXPORT_SYMBOL(fence_timeline_put); >* fence_timeline_destroy - destroy a fence_timeline >* @timeline[in]the fence_timeline to destroy >* > - * This function destroys a timeline. It signals any active fence first. > + * This function destroys a timeline. The implementation for this was certainly broken but I would say it should be fixed to match the comment rather than just abandoned completely. That is, what happens if a timeline owner destroys their timeline while there are outstanding fences which other drivers are waiting on? That is presumably a bug in the code that called destroy prematurely, but bugs happen. The old implementation simply leaked the fences. Doing a debugfs dump would show the timeline with all its outstanding fences still floating around forever after. Worse, anything waiting on them would never be signalled and is therefore potentially deadlocked. Note that I haven't had chance to look through the entire patch series yet so maybe this has been fixed up elsewhere. If not, then I think it definitely needs looking into. >*/ > void fence_timeline_destroy(struct fence_timeline *timeline) > { > @@ -147,10 +147,6 @@ void fence_timeline_destroy(struct fence_timeline > *timeline) >*/ > smp_wmb(); > > - /* > - * signal any children that their parent is going away. > - */ > - fence_timeline_signal(timeline, 0); > fence_timeline_put(timeline); > } > EXPORT_SYMBOL(fence_timeline_destroy);
[PATCH v2 0/2] Add a DRM display driver to the Allwinner H3
The proposed DRM driver works on a Orange PI 2 with a kernel 4.4.0 and the H3 patches found in Hans de Goede's GIT repository. As there is no documentation about the HDMI of the H3, the associated encoder/connector driver has not been included in this patch series. For tests, it may be built as a out-of-tree driver from the tarball: http://moinejf.free.fr/opi2/h3-hdmi.tar.gz and the DT files: http://moinejf.free.fr/opi2/sun8i-h3.dtsi http://moinejf.free.fr/opi2/sun8i-h3-orangepi-plus.dts Jean-Francois Moine (2): clk: sunxi: Add sun6i/8i video support drm: sunxi: Add a basic DRM driver for Allwinner DE2 Documentation/devicetree/bindings/clock/sunxi.txt | 2 + .../devicetree/bindings/display/sunxi.txt | 81 drivers/clk/sunxi/clk-sun6i-display.c | 106 + drivers/clk/sunxi/clk-sun6i-pll3.c | 174 drivers/gpu/drm/Kconfig| 2 + drivers/gpu/drm/Makefile | 1 + drivers/gpu/drm/sunxi/Kconfig | 20 + drivers/gpu/drm/sunxi/Makefile | 7 + drivers/gpu/drm/sunxi/de2_crtc.c | 425 +++ drivers/gpu/drm/sunxi/de2_crtc.h | 43 ++ drivers/gpu/drm/sunxi/de2_de.c | 461 + drivers/gpu/drm/sunxi/de2_drm.h| 55 +++ drivers/gpu/drm/sunxi/de2_drv.c| 376 + drivers/gpu/drm/sunxi/de2_plane.c | 114 + 14 files changed, 1867 insertions(+) create mode 100644 Documentation/devicetree/bindings/display/sunxi.txt create mode 100644 drivers/clk/sunxi/clk-sun6i-display.c create mode 100644 drivers/clk/sunxi/clk-sun6i-pll3.c create mode 100644 drivers/gpu/drm/sunxi/Kconfig create mode 100644 drivers/gpu/drm/sunxi/Makefile create mode 100644 drivers/gpu/drm/sunxi/de2_crtc.c create mode 100644 drivers/gpu/drm/sunxi/de2_crtc.h create mode 100644 drivers/gpu/drm/sunxi/de2_de.c create mode 100644 drivers/gpu/drm/sunxi/de2_drm.h create mode 100644 drivers/gpu/drm/sunxi/de2_drv.c create mode 100644 drivers/gpu/drm/sunxi/de2_plane.c -- 2.7.0
[PATCH v3 2/2] dt-bindings: add document for Innosilicon HDMI on Rockchip platform
Signed-off-by: Yakir Yang Acked-by: Rob Herring --- Changes in v3: None Changes in v2: - Correct the misspell "rk3036-dw-hdmi" (Heiko) .../display/rockchip/inno_hdmi-rockchip.txt| 50 ++ 1 file changed, 50 insertions(+) create mode 100644 Documentation/devicetree/bindings/display/rockchip/inno_hdmi-rockchip.txt diff --git a/Documentation/devicetree/bindings/display/rockchip/inno_hdmi-rockchip.txt b/Documentation/devicetree/bindings/display/rockchip/inno_hdmi-rockchip.txt new file mode 100644 index 000..8096a29 --- /dev/null +++ b/Documentation/devicetree/bindings/display/rockchip/inno_hdmi-rockchip.txt @@ -0,0 +1,50 @@ +Rockchip specific extensions to the Innosilicon HDMI + + +Required properties: +- compatible: + "rockchip,rk3036-inno-hdmi"; +- reg: + Physical base address and length of the controller's registers. +- clocks, clock-names: + Phandle to hdmi controller clock, name should be "pclk" +- interrupts: + HDMI interrupt number +- ports: + Contain one port node with endpoint definitions as defined in + Documentation/devicetree/bindings/graph.txt. +- pinctrl-0, pinctrl-name: + Switch the iomux of HPD/CEC pins to HDMI function. + +Example: +hdmi: hdmi at 20034000 { + compatible = "rockchip,rk3036-inno-hdmi"; + reg = <0x20034000 0x4000>; + interrupts = ; + clocks = < PCLK_HDMI>; + clock-names = "pclk"; + pinctrl-names = "default"; + pinctrl-0 = <_ctl>; + status = "disabled"; + + hdmi_in: port { + #address-cells = <1>; + #size-cells = <0>; + hdmi_in_lcdc: endpoint at 0 { + reg = <0>; + remote-endpoint = <_out_hdmi>; + }; + }; +}; + + { + hdmi { + hdmi_ctl: hdmi-ctl { + rockchip,pins = <1 8 RK_FUNC_1 _pull_none>, + <1 9 RK_FUNC_1 _pull_none>, + <1 10 RK_FUNC_1 _pull_none>, + <1 11 RK_FUNC_1 _pull_none>; + }; + }; + +}; -- 1.9.1
[PATCH v3 0/2] Introduce Innosilicon HDMI driver on Rockchip platforms
Here are a brief introduction to Innosilicon HDMI IP: - Support HDMI 1.4a, HDCP 1.2 and DVI 1.0 standard compliant transmitter - Support HDMI1.4 a/b 3D function defined in HDMI 1.4 a/b spec - Digital video interface supports a pixel size of 24, 30, 36, 48bits color depth in RGB - S/PDIF output supports PCM, Dolby Digital, DTS digital audio transmission (32-192kHz Fs) using IEC60958 and IEC 61937 - The EDID and CEC function are also supported by Innosilicon HDMI Transmitter Controlle This series is based on Mark's RK3036 VOP series, I have created an test branch that collected his changes: [https://github.com/rockchip-linux/kernel/tree/kylin-develop4.4-test] Best regards, - Yakir Changes in v3: - Use encoder enable/disable function, and remove the encoder DPMS function - Keep HDMI PLL power on in standby mode Changes in v2: - Using DRM atomic helper functions for connector init (Mark) - Remove "hdmi->connector.encoder = encoder;" (Mark) - Correct the misspell "rk3036-dw-hdmi" (Heiko) Yakir Yang (2): FORMLIST: drm: rockchip/hdmi: add Innosilicon HDMI support dt-bindings: add document for Innosilicon HDMI on Rockchip platform .../display/rockchip/inno_hdmi-rockchip.txt| 50 ++ drivers/gpu/drm/rockchip/Kconfig | 8 + drivers/gpu/drm/rockchip/Makefile | 1 + drivers/gpu/drm/rockchip/inno_hdmi.c | 999 + drivers/gpu/drm/rockchip/inno_hdmi.h | 364 5 files changed, 1422 insertions(+) create mode 100644 Documentation/devicetree/bindings/display/rockchip/inno_hdmi-rockchip.txt create mode 100644 drivers/gpu/drm/rockchip/inno_hdmi.c create mode 100644 drivers/gpu/drm/rockchip/inno_hdmi.h -- 1.9.1
[PATCH v2 2/2] drm: sunxi: Add a basic DRM driver for Allwinner DE2
In recent SoCs, as the H3, Allwinner uses a new display interface, DE2. This patch adds a DRM video driver for this interface. Signed-off-by: Jean-Francois Moine --- Changes: - remarks from Russell King - DT documentation added - working resolution change with xrandr - removal of the HDMI driver --- .../devicetree/bindings/display/sunxi.txt | 81 drivers/gpu/drm/Kconfig| 2 + drivers/gpu/drm/Makefile | 1 + drivers/gpu/drm/sunxi/Kconfig | 20 + drivers/gpu/drm/sunxi/Makefile | 7 + drivers/gpu/drm/sunxi/de2_crtc.c | 425 +++ drivers/gpu/drm/sunxi/de2_crtc.h | 43 ++ drivers/gpu/drm/sunxi/de2_de.c | 461 + drivers/gpu/drm/sunxi/de2_drm.h| 55 +++ drivers/gpu/drm/sunxi/de2_drv.c| 376 + drivers/gpu/drm/sunxi/de2_plane.c | 114 + 11 files changed, 1585 insertions(+) create mode 100644 Documentation/devicetree/bindings/display/sunxi.txt create mode 100644 drivers/gpu/drm/sunxi/Kconfig create mode 100644 drivers/gpu/drm/sunxi/Makefile create mode 100644 drivers/gpu/drm/sunxi/de2_crtc.c create mode 100644 drivers/gpu/drm/sunxi/de2_crtc.h create mode 100644 drivers/gpu/drm/sunxi/de2_de.c create mode 100644 drivers/gpu/drm/sunxi/de2_drm.h create mode 100644 drivers/gpu/drm/sunxi/de2_drv.c create mode 100644 drivers/gpu/drm/sunxi/de2_plane.c diff --git a/Documentation/devicetree/bindings/display/sunxi.txt b/Documentation/devicetree/bindings/display/sunxi.txt new file mode 100644 index 000..1070bf0 --- /dev/null +++ b/Documentation/devicetree/bindings/display/sunxi.txt @@ -0,0 +1,81 @@ +Allwinner sunxi display subsystem += + +The sunxi display subsystems contain a display controller (DE), +one or two LCD controllers (TCON) and their external interfaces. + +Display controller +== + +Required properties: + +- compatible: value should be one of the following + "allwinner,sun8i-h3-display-engine" + +- clocks: must include clock specifiers corresponding to entries in the + clock-names property. + +- clock-names: must contain + gate: for DE activation + clock: DE clock + +- resets: phandle to the reset of the device + +- ports: phandle's to the LCD ports + +LCD controller +== + +Required properties: + +- compatible: value should be one of the following + "allwinner,sun8i-h3-lcd" + +- clocks: must include clock specifiers corresponding to entries in the + clock-names property. + +- clock-names: must contain + gate: for LCD activation + clock: pixel clock + +- resets: phandle to the reset of the device + +- port: port node with endpoint definitions as defined in + Documentation/devicetree/bindings/media/video-interfaces.txt + +Example: + + de: de-controller at 0100 { + compatible = "allwinner,sun8i-h3-display-engine"; + ... + clocks = <_gates 44>, <_clk>; + clock-names = "gate", "clock"; + resets = <_rst 44>; + ports = <_p>; + }; + + lcd0: lcd-controller at 01c0c000 { + compatible = "allwinner,sun8i-h3-lcd"; + ... + clocks = <_gates 35>, <_clk>; + clock-names = "gate", "clock"; + resets = <_rst 35>; + #address-cells = <1>; + #size-cells = <0>; + lcd0_p: port { + lcd0_ep: endpoint { + remote-endpoint = <_ep>; + }; + }; + }; + + hdmi: hdmi at 01ee { + ... + #address-cells = <1>; + #size-cells = <0>; + port { + hdmi_ep: endpoint { + remote-endpoint = <_ep>; + }; + }; + }; diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig index c4bf9a1..edef0c8 100644 --- a/drivers/gpu/drm/Kconfig +++ b/drivers/gpu/drm/Kconfig @@ -266,3 +266,5 @@ source "drivers/gpu/drm/amd/amdkfd/Kconfig" source "drivers/gpu/drm/imx/Kconfig" source "drivers/gpu/drm/vc4/Kconfig" + +source "drivers/gpu/drm/sunxi/Kconfig" diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile index 1e9ff4c..597c246 100644 --- a/drivers/gpu/drm/Makefile +++ b/drivers/gpu/drm/Makefile @@ -75,3 +75,4 @@ obj-y += i2c/ obj-y += panel/ obj-y += bridge/ obj-$(CONFIG_DRM_FSL_DCU) += fsl-dcu/ +obj-$(CONFIG_DRM_SUNXI) += sunxi/ diff --git a/drivers/gpu/drm/sunxi/Kconfig b/drivers/gpu/drm/sunxi/Kconfig new file mode 100644 index
[PATCH v2 02/26] reset: Make reset_control_ops const
Am Donnerstag, den 14.01.2016, 16:24 +0100 schrieb Maxime Ripard: > The ops pointer is holding a pointer to a structure that is usually not > modified. Make it const. > > Signed-off-by: Maxime Ripard > --- > include/linux/reset-controller.h | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/include/linux/reset-controller.h > b/include/linux/reset-controller.h > index ce6b962ffed4..a3a5bcdb1d02 100644 > --- a/include/linux/reset-controller.h > +++ b/include/linux/reset-controller.h > @@ -38,7 +38,7 @@ struct of_phandle_args; > * @nr_resets: number of reset controls in this reset controller device > */ > struct reset_controller_dev { > - struct reset_control_ops *ops; > + const struct reset_control_ops *ops; > struct module *owner; > struct list_head list; > struct device_node *of_node; Applied, thanks. regards Philipp
[PATCH v2 01/26] reset: Move DT cell size check to the core
Hi Maxime, Am Donnerstag, den 14.01.2016, 16:24 +0100 schrieb Maxime Ripard: > The core currently doesn't check that the DT cell size matches what the > driver declares, which means that every xlate function needs to duplicate > that check. > > Make sure that of_reset_control_get checks for this to avoid duplication > and errors. > > Signed-off-by: Maxime Ripard > --- > drivers/reset/core.c | 6 +++--- > 1 file changed, 3 insertions(+), 3 deletions(-) > > diff --git a/drivers/reset/core.c b/drivers/reset/core.c > index 7955e00d04d4..d53b2b980bdd 100644 > --- a/drivers/reset/core.c > +++ b/drivers/reset/core.c > @@ -46,9 +46,6 @@ struct reset_control { > static int of_reset_simple_xlate(struct reset_controller_dev *rcdev, > const struct of_phandle_args *reset_spec) > { > - if (WARN_ON(reset_spec->args_count != rcdev->of_reset_n_cells)) > - return -EINVAL; > - > if (reset_spec->args[0] >= rcdev->nr_resets) > return -EINVAL; > > @@ -182,6 +179,9 @@ struct reset_control *of_reset_control_get(struct > device_node *node, > return ERR_PTR(-EPROBE_DEFER); > } > > + if (WARN_ON(args.args_count != rcdev->of_reset_n_cells)) > + return ERR_PTR(-EINVAL); > + Applied with this fix: - if (WARN_ON(args.args_count != rcdev->of_reset_n_cells)) + if (WARN_ON(args.args_count != rcdev->of_reset_n_cells)) { + mutex_unlock(_controller_list_mutex); return ERR_PTR(-EINVAL); + } No further action needed if you agree, otherwise let me know and I'll back it out. best regards Philipp
[PATCH v2 1/2] clk: sunxi: Add sun6i/8i video support
Add the clock types which are used by the sun6i/8i families for video. Signed-off-by: Jean-Francois Moine --- Changes: - remarks from Chen-Yu Tsai - DT documentation added --- Documentation/devicetree/bindings/clock/sunxi.txt | 2 + drivers/clk/sunxi/clk-sun6i-display.c | 106 + drivers/clk/sunxi/clk-sun6i-pll3.c| 174 ++ 3 files changed, 282 insertions(+) create mode 100644 drivers/clk/sunxi/clk-sun6i-display.c create mode 100644 drivers/clk/sunxi/clk-sun6i-pll3.c diff --git a/Documentation/devicetree/bindings/clock/sunxi.txt b/Documentation/devicetree/bindings/clock/sunxi.txt index 8a47b77..c57dd0e 100644 --- a/Documentation/devicetree/bindings/clock/sunxi.txt +++ b/Documentation/devicetree/bindings/clock/sunxi.txt @@ -11,6 +11,7 @@ Required properties: "allwinner,sun6i-a31-pll1-clk" - for the main PLL clock on A31 "allwinner,sun8i-a23-pll1-clk" - for the main PLL clock on A23 "allwinner,sun9i-a80-pll4-clk" - for the peripheral PLLs on A80 + "allwinner,sun6i-pll3-clk" - for the video PLLs clock "allwinner,sun4i-a10-pll5-clk" - for the PLL5 clock "allwinner,sun4i-a10-pll6-clk" - for the PLL6 clock "allwinner,sun6i-a31-pll6-clk" - for the PLL6 clock on A31 @@ -70,6 +71,7 @@ Required properties: "allwinner,sun8i-a23-usb-clk" - for usb gates + resets on A23 "allwinner,sun9i-a80-usb-mod-clk" - for usb gates + resets on A80 "allwinner,sun9i-a80-usb-phy-clk" - for usb phy gates + resets on A80 + "allwinner,sun6i-display-clk" - for the display clocks Required properties for all clocks: - reg : shall be the control register address for the clock. diff --git a/drivers/clk/sunxi/clk-sun6i-display.c b/drivers/clk/sunxi/clk-sun6i-display.c new file mode 100644 index 000..48356e3 --- /dev/null +++ b/drivers/clk/sunxi/clk-sun6i-display.c @@ -0,0 +1,106 @@ +/* + * Copyright 2016 Jean-Francois Moine + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * 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 +#include +#include + +static DEFINE_SPINLOCK(sun6i_display_lock); + +#define SUN6I_DISPLAY_GATE_BIT 31 +#define SUN6I_DISPLAY_SEL_SHIFT24 +#define SUN6I_DISPLAY_SEL_MASK GENMASK(2, 0) +#define SUN6I_DISPLAY_MSHIFT 0 +#define SUN6I_DISPLAY_MWIDTH 4 + +static void __init sun6i_display_setup(struct device_node *node) +{ + const char *clk_name = node->name; + const char *parents[8]; + struct clk_mux *mux = NULL; + struct clk_divider *div; + struct clk_gate *gate; + struct resource res; + void __iomem *mmio; + struct clk *clk; + int n; + + of_property_read_string(node, "clock-output-names", _name); + + mmio = of_io_request_and_map(node, 0, of_node_full_name(node)); + if (IS_ERR(mmio)) { + pr_err("%s: Could not map the clock registers\n", clk_name); + return; + } + + n = of_clk_parent_fill(node, parents, ARRAY_SIZE(parents)); + + if (n > 1) {/* many possible sources */ + mux = kzalloc(sizeof(*mux), GFP_KERNEL); + if (!mux) + goto free_io; + mux->reg = mmio; + mux->shift = SUN6I_DISPLAY_SEL_SHIFT; + mux->mask = SUN6I_DISPLAY_SEL_MASK; + mux->lock = _display_lock; + } + + gate = kzalloc(sizeof(*gate), GFP_KERNEL); + if (!gate) + goto free_mux; + + gate->reg = mmio; + gate->bit_idx = SUN6I_DISPLAY_GATE_BIT; + gate->lock = _display_lock; + + div = kzalloc(sizeof(*div), GFP_KERNEL); + if (!div) + goto free_gate; + + div->reg = mmio; + div->shift = SUN6I_DISPLAY_MSHIFT; + div->width = SUN6I_DISPLAY_MWIDTH; + div->lock = _display_lock; + + clk = clk_register_composite(NULL, clk_name, +parents, n, +mux ? >hw : NULL, _mux_ops, +>hw, _divider_ops, +>hw, _gate_ops, +0); + if (IS_ERR(clk)) { + pr_err("%s: Couldn't register the clock\n", clk_name); + goto free_div; + } + + of_clk_add_provider(node, of_clk_src_simple_get, clk); + + return; + +free_div: + kfree(div); +free_gate: + kfree(gate); +free_mux: +
Lockdep warning when using REGCACHE_RBTREE
On Thu, Jan 14, 2016 at 05:14:47PM -0800, Stefan Agner wrote: > On a slightly other topic, I question whether REGCACHE_RBTREE is the > right cache type for the DCU DRM driver. The driver has uses a regmap > area of 1144 32-bit registers, the most space is used by the layer > configuration registers which are 0x40 apart and 0x0-0x20 for each layer > are actually used (hence somewhat above 50%). > Would FLAT be the better cache type? Yes, and if it's a MMIO device the performance of a flat cache is more in line with the device performance. -- next part -- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 473 bytes Desc: not available URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/8a5c229d/attachment.sig>
[PATCH] configure.ac: disable annoying warning -Wmissing-field-initializers
On Fri, Jan 15, 2016 at 12:12 PM, Emil Velikov wrote: > On 12 January 2016 at 23:14, Marek Olšák wrote: >> From: Marek Olšák >> >> It warns for all "{}" initializers. Well, I want us to use {}. >> --- >> configure.ac | 3 ++- >> intel/intel_decode.c | 2 -- > The whole of libdrm, minus the intel_decode can get away without using > such constructs. And yes that includes radeon and amdgpu. > > NACK on this one - please be consistent with existing code base. Consistent with what? {} is the same as memset on each structure member. The warning says that a structure member is initialized to zero because of {}, which is why {} is used in the first place. It's the same as using memset and getting a warning "memset initializes the memory to zero". How useful is that? libdrm does have a lot of optional warnings enabled. Mesa does not, and Mesa does not even have this one. This means libdrm is inconsistent with Mesa and, BTW, it's also inconsistent with the kernel. It looks like somebody enabled optional warnings for libdrm in the past. All I'm doing is aligning the behavior with Mesa/kernel, which is what we would like to have and so would Intel apparently. Do you still think we are inconsistent? Thanks, Marek
[RFC 26/29] dma-buf/fence: remove pointless fence_timeline_signal at destroy phase
2016-01-15 John Harrison : > On 15/01/2016 14:55, Gustavo Padovan wrote: > >From: Gustavo Padovan > > > >All changes to timeline value come through the user via > >fence_timeline_signal() calls. When fence_timeline_destroy() is called no > >changes on timeline->value happens hence call fence_timeline_signal() with > >no increment is pointless. > > > >Signed-off-by: Gustavo Padovan > >--- > > drivers/dma-buf/fence.c | 6 +- > > 1 file changed, 1 insertion(+), 5 deletions(-) > > > >diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c > >index 7a5fc9b..26f5f0f 100644 > >--- a/drivers/dma-buf/fence.c > >+++ b/drivers/dma-buf/fence.c > >@@ -136,7 +136,7 @@ EXPORT_SYMBOL(fence_timeline_put); > > * fence_timeline_destroy - destroy a fence_timeline > > * @timeline [in]the fence_timeline to destroy > > * > >- * This function destroys a timeline. It signals any active fence first. > >+ * This function destroys a timeline. > > The implementation for this was certainly broken but I would say it should > be fixed to match the comment rather than just abandoned completely. That > is, what happens if a timeline owner destroys their timeline while there are > outstanding fences which other drivers are waiting on? That is presumably a > bug in the code that called destroy prematurely, but bugs happen. > > The old implementation simply leaked the fences. Doing a debugfs dump would > show the timeline with all its outstanding fences still floating around > forever after. Worse, anything waiting on them would never be signalled and > is therefore potentially deadlocked. > > Note that I haven't had chance to look through the entire patch series yet > so maybe this has been fixed up elsewhere. If not, then I think it > definitely needs looking into. > Patches 27 and 28 are attempt to fix that. I assumed that if some code is calling fence_timeline_destroy() it wants to stop everything so I worked on a solution that stops any waiter and allows the timeline to be destroyed. No one is using fence_timeline_destroy() in mainline now, so it is definately a behaviour we can discuss. Gustavo
[Bug 93548] Grid Autosport causes a hard system crash
https://bugs.freedesktop.org/show_bug.cgi?id=93548 --- Comment #3 from Edwin Smith --- I am pretty sure this is the bug with xpad that can cause hangs when using force feedback. This was reported by Feral during development of XCOM and was fixed for SteamOS by Pierre-Loup but the fix has not made it's way upstream to the main linux kernel. This was fixed by Sarah Bessmer (see link here) http://www.spinics.net/lists/linux-input/msg31450.html Pierre-Loup also fixed the issue separately himself for the SteamOS drivers. Sarah's fix has been used by a number of people with a lot of success and we have also confirmed the SteamOS drivers don't see this issue so hopefully one of the two fixes can be merged into xpad to fix this problem. Hope this background helps! -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/0af42b8d/attachment.html>
[RFC 26/29] dma-buf/fence: remove pointless fence_timeline_signal at destroy phase
On 01/15/2016 10:02 AM, Gustavo Padovan wrote: > Patches 27 and 28 are attempt to fix that. I assumed that if some code is > calling fence_timeline_destroy() it wants to stop everything so I > worked on a solution that stops any waiter and allows the timeline to be > destroyed. > > No one is using fence_timeline_destroy() in mainline now, so it is > definately a behaviour we can discuss. > > Gustavo > +Tom Cherry and Dmitry Torokhov recently discovered that this was broken by the refactoring of Android sync on top of dma-buf fences. Tom and Dmitry, did you send the proposed fix upstream?
[Bug 93713] System hangs (beomes totaly unresponsive) when trying to use hybrid graphics with ATI 7730M videocard
https://bugs.freedesktop.org/show_bug.cgi?id=93713 --- Comment #3 from Alex Deucher --- Please attach your dmesg output when after it hangs. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/d4cf3346/attachment.html>
[PATCH RFC] drm/i2c: tda998x: Only set atomic funcs if bound to atomic drm driver
Only set atomic connector callbacks if the tda998x driver is bound to a drm driver that supports atomic modesetting. At least drm_crtc_helper_set_config() calls connectors dpms callback without knowing that it may assume atomic modeset support. Calling drm_atomic_helper_connector_dpms() causes a crash with a driver that does not have atomic state initialized. Fixes commit 9736e988d328 ("drm/i2c: tda998x: Add support for atomic modesetting"). Signed-off-by: Jyri Sarha --- I am not sure if this is the best way to fix the issue, but after 9736e988d328 Beaglebone-Black HDMI is totally broken and this fixes the issue. I am currently working on atomic modesetting for tilcdc, but there is no way it makes it to 4.5 release. Best regards, Jyri drivers/gpu/drm/i2c/tda998x_drv.c | 17 +++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i2c/tda998x_drv.c b/drivers/gpu/drm/i2c/tda998x_drv.c index 012d36d..67d1408 100644 --- a/drivers/gpu/drm/i2c/tda998x_drv.c +++ b/drivers/gpu/drm/i2c/tda998x_drv.c @@ -1382,7 +1382,7 @@ static void tda998x_connector_destroy(struct drm_connector *connector) drm_connector_cleanup(connector); } -static const struct drm_connector_funcs tda998x_connector_funcs = { +static const struct drm_connector_funcs tda998x_connector_atomic_funcs = { .dpms = drm_atomic_helper_connector_dpms, .reset = drm_atomic_helper_connector_reset, .fill_modes = drm_helper_probe_single_connector_modes, @@ -1392,15 +1392,28 @@ static const struct drm_connector_funcs tda998x_connector_funcs = { .atomic_destroy_state = drm_atomic_helper_connector_destroy_state, }; +static const struct drm_connector_funcs tda998x_connector_funcs = { + .dpms = drm_helper_connector_dpms, + .fill_modes = drm_helper_probe_single_connector_modes, + .detect = tda998x_connector_detect, + .destroy = tda998x_connector_destroy, +}; + static int tda998x_bind(struct device *dev, struct device *master, void *data) { struct tda998x_encoder_params *params = dev->platform_data; struct i2c_client *client = to_i2c_client(dev); struct drm_device *drm = data; struct tda998x_priv *priv; + const struct drm_connector_funcs *connector_funcs; u32 crtcs = 0; int ret; + if (drm_core_check_feature(drm, DRIVER_ATOMIC)) + connector_funcs = _connector_atomic_funcs; + else + connector_funcs = _connector_funcs; + priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); if (!priv) return -ENOMEM; @@ -1437,7 +1450,7 @@ static int tda998x_bind(struct device *dev, struct device *master, void *data) drm_connector_helper_add(>connector, _connector_helper_funcs); ret = drm_connector_init(drm, >connector, -_connector_funcs, +connector_funcs, DRM_MODE_CONNECTOR_HDMIA); if (ret) goto err_connector; -- 1.9.1
[Bug 93534] Issues with color and rendering through OpenGL composited desktops on ATI FirePro v4800
https://bugs.freedesktop.org/show_bug.cgi?id=93534 Sawyer Bergeron changed: What|Removed |Added Severity|normal |major --- Comment #6 from Sawyer Bergeron --- Changing status to medium-major, as although this likely only affects a couple users it is of major importance to those users as it causes an inability to normally use Mesa and is a persistent, system wide, issue. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/d3077226/attachment.html>
linux-4.4 bisected: kwin5 stuck on kde5 loading screen with radeon
On Fri, Jan 15, 2016 at 11:34:08AM +0100, Vlastimil Babka wrote: > Hi, > > since kernel 4.4 I'm unable to login to kde5 desktop (on openSUSE > Tumbleweed). There's a screen with progressbar showing the startup, > which normally fades away after reaching 100%. But with kernel 4.4, the > progress gets stuck somewhere between 1/2 and 3/4 (not always the same). > Top shows that kwin is using few % of CPU's but mostly sleeps in poll(). > When I kill it from another console, I see that everything has actually > started up, just the progressbar screen was obscuring it. The windows > obviously don't have decorations etc. Starting kwin manually again shows > me again the progressbar screen at the same position. Hmm. Sounds like it could then be waiting for a vblank in the distant future. There's that 1<<23 limit in the code though, but even with that we end up with a max wait of ~38 hours assuming a 60Hz refresh rate. Stuff to try might include enabling drm.debug=0x2f, though that'll generate a lot of stuff. Another option would be to use the drm vblank tracepoints to try and catch what seq number it's waiting for and where we're at currently. Or I suppose you could just hack up drm_wait_vblank() to print an error message or something if the requested seq number is in the future by, say, more than a few seconds, and if that's the case then we could try to figure out why that happens. > > I have suspected that kwin is waiting for some event, but nevertheless > tried bisecting the kernel between 4.3 and 4.4, which lead to: > > # first bad commit: [4dfd64862ff852df7b1198d667dda778715ee88f] drm: Use > vblank timestamps to guesstimate how many vblanks were missed > > I can confirm that 4.4 works if I revert the following commits: > 63154ff230fc9255cc507af6277cd181943c50a1 "drm/amdgpu: Fixup hw vblank > counter/ts for new drm_update_vblank_count() (v3)" > > d1145ad1e41b6c33758a856163198cb53bb96a50 "drm/radeon: Fixup hw vblank > counter/ts for new drm_update_vblank_count() (v2)" The sha1s don't seem to match what I have, so not sure which kernel tree you have, but looking at the radeon commit at least one thing immediately caught my attention; + /* Bump counter if we are at >= leading edge of vblank, +* but before vsync where vpos would turn negative and +* the hw counter really increments. +*/ + if (vpos >= 0) + count++; It's rather hard to see what it's really doing since the custom flags to the get_scanout_position now cause it return non-standard things. But if I'm reading things correctly it should really say something like: if (vpos >= 0 && vpos < (vsync_start - vblank_start)) count++; Hmm. Actually even that might not be correct since it could be using the "fake" vblank start here, so might be it'd need to be something like: if (vpos >= 0 && vpos < (vsync_start - vblank_start + lb_vblank_lead_lines) count++; Also might be worth a shot to just ignore the hw frame counter. Eg.: index e266ffc520d2..db728580549a 100644 --- a/drivers/gpu/drm/radeon/radeon_drv.c +++ b/drivers/gpu/drm/radeon/radeon_drv.c @@ -492,7 +492,6 @@ static struct drm_driver kms_driver = { .lastclose = radeon_driver_lastclose_kms, .set_busid = drm_pci_set_busid, .unload = radeon_driver_unload_kms, - .get_vblank_counter = radeon_get_vblank_counter_kms, .enable_vblank = radeon_enable_vblank_kms, .disable_vblank = radeon_disable_vblank_kms, .get_vblank_timestamp = radeon_get_vblank_timestamp_kms, diff --git a/drivers/gpu/drm/radeon/radeon_irq_kms.c b/drivers/gpu/drm/radeon/radeon_irq_kms.c index 979f3bf65f2c..3c5fcab74152 100644 --- a/drivers/gpu/drm/radeon/radeon_irq_kms.c +++ b/drivers/gpu/drm/radeon/radeon_irq_kms.c @@ -152,11 +152,6 @@ int radeon_driver_irq_postinstall_kms(struct drm_device *dev) { struct radeon_device *rdev = dev->dev_private; - if (ASIC_IS_AVIVO(rdev)) - dev->max_vblank_count = 0x00ff; - else - dev->max_vblank_count = 0x001f; - return 0; } assuming I'm reading the code correctly. > > 31ace027c9f1f8e0a2b09bbf961e4db7b1f6cf19 "drm: Don't zero vblank > timestamps from the irq handler" > > ac0567a4b132fa66e3edf3f913938af9daf7f916 "drm: Add DRM_DEBUG_VBL()" > > 4dfd64862ff852df7b1198d667dda778715ee88f "drm: Use vblank timestamps to > guesstimate how many vblanks were missed" > > All clean reverts, just needs some fixup on top to use abs() instead of > abs64() due to 79211c8ed19c055ca105502c8733800d442a0ae6. > > Unfortunately I don't know if this is a kernel problem or kwin problem. > I tried to CC maintainers of both, advices what to try or what info to > provide welcome. The card is "CAICOS" with 1GB memory. > > Thanks, > Vlastimil -- Ville Syrjälä Intel OTC
[PATCH RFC] drm/i2c: tda998x: Only set atomic funcs if bound to atomic drm driver
On Fri, Jan 15, 2016 at 02:55:26PM +0200, Jyri Sarha wrote: > Only set atomic connector callbacks if the tda998x driver is bound to > a drm driver that supports atomic modesetting. At least > drm_crtc_helper_set_config() calls connectors dpms callback without > knowing that it may assume atomic modeset support. Calling > drm_atomic_helper_connector_dpms() causes a crash with a driver that > does not have atomic state initialized. Hi Jyri, > > Fixes commit 9736e988d328 ("drm/i2c: tda998x: Add support for atomic > modesetting"). First, sorry for the breakage, I did not had any other board to test the change on. > > Signed-off-by: Jyri Sarha > --- > I am not sure if this is the best way to fix the issue, but after > 9736e988d328 Beaglebone-Black HDMI is totally broken and this fixes > the issue. I am currently working on atomic modesetting for tilcdc, > but there is no way it makes it to 4.5 release. Yes, I'm not a big fan of the change either. I would've thought that you only need to update the .dpms pointer, all other hooks added are specific to atomic operations (right?). Would it not be simpler to have a tda998x_connector_dpms() function that calls the appropriate .dpms function based on the feature check? Best regards, Liviu > > Best regards, > Jyri > > drivers/gpu/drm/i2c/tda998x_drv.c | 17 +++-- > 1 file changed, 15 insertions(+), 2 deletions(-) > > diff --git a/drivers/gpu/drm/i2c/tda998x_drv.c > b/drivers/gpu/drm/i2c/tda998x_drv.c > index 012d36d..67d1408 100644 > --- a/drivers/gpu/drm/i2c/tda998x_drv.c > +++ b/drivers/gpu/drm/i2c/tda998x_drv.c > @@ -1382,7 +1382,7 @@ static void tda998x_connector_destroy(struct > drm_connector *connector) > drm_connector_cleanup(connector); > } > > -static const struct drm_connector_funcs tda998x_connector_funcs = { > +static const struct drm_connector_funcs tda998x_connector_atomic_funcs = { > .dpms = drm_atomic_helper_connector_dpms, > .reset = drm_atomic_helper_connector_reset, > .fill_modes = drm_helper_probe_single_connector_modes, > @@ -1392,15 +1392,28 @@ static const struct drm_connector_funcs > tda998x_connector_funcs = { > .atomic_destroy_state = drm_atomic_helper_connector_destroy_state, > }; > > +static const struct drm_connector_funcs tda998x_connector_funcs = { > + .dpms = drm_helper_connector_dpms, > + .fill_modes = drm_helper_probe_single_connector_modes, > + .detect = tda998x_connector_detect, > + .destroy = tda998x_connector_destroy, > +}; > + > static int tda998x_bind(struct device *dev, struct device *master, void > *data) > { > struct tda998x_encoder_params *params = dev->platform_data; > struct i2c_client *client = to_i2c_client(dev); > struct drm_device *drm = data; > struct tda998x_priv *priv; > + const struct drm_connector_funcs *connector_funcs; > u32 crtcs = 0; > int ret; > > + if (drm_core_check_feature(drm, DRIVER_ATOMIC)) > + connector_funcs = _connector_atomic_funcs; > + else > + connector_funcs = _connector_funcs; > + > priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); > if (!priv) > return -ENOMEM; > @@ -1437,7 +1450,7 @@ static int tda998x_bind(struct device *dev, struct > device *master, void *data) > drm_connector_helper_add(>connector, >_connector_helper_funcs); > ret = drm_connector_init(drm, >connector, > - _connector_funcs, > + connector_funcs, >DRM_MODE_CONNECTOR_HDMIA); > if (ret) > goto err_connector; > -- > 1.9.1 > > ___ > dri-devel mailing list > dri-devel at lists.freedesktop.org > http://lists.freedesktop.org/mailman/listinfo/dri-devel -- | I would like to | | fix the world, | | but they're not | | giving me the | \ source code! / --- ¯\_(ã)_/¯
[PATCH 7/7] drm/amdgpu: drop hard_reset module parameter
It doesn't currently do anything and there's no need for it going forward since pci config reset will be required as a fallback even when we have fine grained reset implemented. Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu.h | 1 - drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 4 2 files changed, 5 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu.h b/drivers/gpu/drm/amd/amdgpu/amdgpu.h index ce061d3..7cc76e2 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu.h @@ -76,7 +76,6 @@ extern int amdgpu_dpm; extern int amdgpu_smc_load_fw; extern int amdgpu_aspm; extern int amdgpu_runtime_pm; -extern int amdgpu_hard_reset; extern unsigned amdgpu_ip_block_mask; extern int amdgpu_bapm; extern int amdgpu_deep_color; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c index 99031ec..371f30d 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c @@ -69,7 +69,6 @@ int amdgpu_dpm = -1; int amdgpu_smc_load_fw = 1; int amdgpu_aspm = -1; int amdgpu_runtime_pm = -1; -int amdgpu_hard_reset = 0; unsigned amdgpu_ip_block_mask = 0x; int amdgpu_bapm = -1; int amdgpu_deep_color = 0; @@ -125,9 +124,6 @@ module_param_named(aspm, amdgpu_aspm, int, 0444); MODULE_PARM_DESC(runpm, "PX runtime pm (1 = force enable, 0 = disable, -1 = PX only default)"); module_param_named(runpm, amdgpu_runtime_pm, int, 0444); -MODULE_PARM_DESC(hard_reset, "PCI config reset (1 = force enable, 0 = disable (default))"); -module_param_named(hard_reset, amdgpu_hard_reset, int, 0444); - MODULE_PARM_DESC(ip_block_mask, "IP Block Mask (all blocks enabled (default))"); module_param_named(ip_block_mask, amdgpu_ip_block_mask, uint, 0444); -- 2.5.0
[PATCH 6/7] drm/amdgpu: add a debugfs property to trigger a GPU reset
Ported from similar code in radeon. Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c | 20 +++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c index cac03e7..697fb45 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c @@ -806,15 +806,33 @@ static int amdgpu_debugfs_fence_info(struct seq_file *m, void *data) return 0; } +/** + * amdgpu_debugfs_gpu_reset - manually trigger a gpu reset + * + * Manually trigger a gpu reset at the next fence wait. + */ +static int amdgpu_debugfs_gpu_reset(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct drm_device *dev = node->minor->dev; + struct amdgpu_device *adev = dev->dev_private; + + seq_printf(m, "gpu reset\n"); + amdgpu_gpu_reset(adev); + + return 0; +} + static struct drm_info_list amdgpu_debugfs_fence_list[] = { {"amdgpu_fence_info", _debugfs_fence_info, 0, NULL}, + {"amdgpu_gpu_reset", _debugfs_gpu_reset, 0, NULL} }; #endif int amdgpu_debugfs_fence_init(struct amdgpu_device *adev) { #if defined(CONFIG_DEBUG_FS) - return amdgpu_debugfs_add_files(adev, amdgpu_debugfs_fence_list, 1); + return amdgpu_debugfs_add_files(adev, amdgpu_debugfs_fence_list, 2); #else return 0; #endif -- 2.5.0
[PATCH 5/7] drm/amdgpu: post card after hard reset
Posting is required after a pci config reset. Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c index 9d9d425e..7932ace 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c @@ -1890,6 +1890,9 @@ int amdgpu_gpu_reset(struct amdgpu_device *adev) retry: r = amdgpu_asic_reset(adev); + /* post card */ + amdgpu_atom_asic_init(adev->mode_info.atom_context); + if (!r) { dev_info(adev->dev, "GPU reset succeeded, trying to resume\n"); r = amdgpu_resume(adev); -- 2.5.0
[PATCH 4/7] drm/amdgpu: clean up asic level reset for VI
Drop soft reset, always use pci config reset. Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/vi.c | 385 +--- 1 file changed, 4 insertions(+), 381 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/vi.c b/drivers/gpu/drm/amd/amdgpu/vi.c index d5e02e1..48b2ca1 100644 --- a/drivers/gpu/drm/amd/amdgpu/vi.c +++ b/drivers/gpu/drm/amd/amdgpu/vi.c @@ -574,374 +574,12 @@ static int vi_read_register(struct amdgpu_device *adev, u32 se_num, return -EINVAL; } -static void vi_print_gpu_status_regs(struct amdgpu_device *adev) -{ - dev_info(adev->dev, " GRBM_STATUS=0x%08X\n", - RREG32(mmGRBM_STATUS)); - dev_info(adev->dev, " GRBM_STATUS2=0x%08X\n", - RREG32(mmGRBM_STATUS2)); - dev_info(adev->dev, " GRBM_STATUS_SE0=0x%08X\n", - RREG32(mmGRBM_STATUS_SE0)); - dev_info(adev->dev, " GRBM_STATUS_SE1=0x%08X\n", - RREG32(mmGRBM_STATUS_SE1)); - dev_info(adev->dev, " GRBM_STATUS_SE2=0x%08X\n", - RREG32(mmGRBM_STATUS_SE2)); - dev_info(adev->dev, " GRBM_STATUS_SE3=0x%08X\n", - RREG32(mmGRBM_STATUS_SE3)); - dev_info(adev->dev, " SRBM_STATUS=0x%08X\n", - RREG32(mmSRBM_STATUS)); - dev_info(adev->dev, " SRBM_STATUS2=0x%08X\n", - RREG32(mmSRBM_STATUS2)); - dev_info(adev->dev, " SDMA0_STATUS_REG = 0x%08X\n", - RREG32(mmSDMA0_STATUS_REG + SDMA0_REGISTER_OFFSET)); - if (adev->sdma.num_instances > 1) { - dev_info(adev->dev, " SDMA1_STATUS_REG = 0x%08X\n", - RREG32(mmSDMA0_STATUS_REG + SDMA1_REGISTER_OFFSET)); - } - dev_info(adev->dev, " CP_STAT = 0x%08x\n", RREG32(mmCP_STAT)); - dev_info(adev->dev, " CP_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT1)); - dev_info(adev->dev, " CP_STALLED_STAT2 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT2)); - dev_info(adev->dev, " CP_STALLED_STAT3 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT3)); - dev_info(adev->dev, " CP_CPF_BUSY_STAT = 0x%08x\n", -RREG32(mmCP_CPF_BUSY_STAT)); - dev_info(adev->dev, " CP_CPF_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_CPF_STALLED_STAT1)); - dev_info(adev->dev, " CP_CPF_STATUS = 0x%08x\n", RREG32(mmCP_CPF_STATUS)); - dev_info(adev->dev, " CP_CPC_BUSY_STAT = 0x%08x\n", RREG32(mmCP_CPC_BUSY_STAT)); - dev_info(adev->dev, " CP_CPC_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_CPC_STALLED_STAT1)); - dev_info(adev->dev, " CP_CPC_STATUS = 0x%08x\n", RREG32(mmCP_CPC_STATUS)); -} - -/** - * vi_gpu_check_soft_reset - check which blocks are busy - * - * @adev: amdgpu_device pointer - * - * Check which blocks are busy and return the relevant reset - * mask to be used by vi_gpu_soft_reset(). - * Returns a mask of the blocks to be reset. - */ -u32 vi_gpu_check_soft_reset(struct amdgpu_device *adev) -{ - u32 reset_mask = 0; - u32 tmp; - - /* GRBM_STATUS */ - tmp = RREG32(mmGRBM_STATUS); - if (tmp & (GRBM_STATUS__PA_BUSY_MASK | GRBM_STATUS__SC_BUSY_MASK | - GRBM_STATUS__BCI_BUSY_MASK | GRBM_STATUS__SX_BUSY_MASK | - GRBM_STATUS__TA_BUSY_MASK | GRBM_STATUS__VGT_BUSY_MASK | - GRBM_STATUS__DB_BUSY_MASK | GRBM_STATUS__CB_BUSY_MASK | - GRBM_STATUS__GDS_BUSY_MASK | GRBM_STATUS__SPI_BUSY_MASK | - GRBM_STATUS__IA_BUSY_MASK | GRBM_STATUS__IA_BUSY_NO_DMA_MASK)) - reset_mask |= AMDGPU_RESET_GFX; - - if (tmp & (GRBM_STATUS__CP_BUSY_MASK | GRBM_STATUS__CP_COHERENCY_BUSY_MASK)) - reset_mask |= AMDGPU_RESET_CP; - - /* GRBM_STATUS2 */ - tmp = RREG32(mmGRBM_STATUS2); - if (tmp & GRBM_STATUS2__RLC_BUSY_MASK) - reset_mask |= AMDGPU_RESET_RLC; - - if (tmp & (GRBM_STATUS2__CPF_BUSY_MASK | - GRBM_STATUS2__CPC_BUSY_MASK | - GRBM_STATUS2__CPG_BUSY_MASK)) - reset_mask |= AMDGPU_RESET_CP; - - /* SRBM_STATUS2 */ - tmp = RREG32(mmSRBM_STATUS2); - if (tmp & SRBM_STATUS2__SDMA_BUSY_MASK) - reset_mask |= AMDGPU_RESET_DMA; - - if (tmp & SRBM_STATUS2__SDMA1_BUSY_MASK) - reset_mask |= AMDGPU_RESET_DMA1; - - /* SRBM_STATUS */ - tmp = RREG32(mmSRBM_STATUS); - - if (tmp & SRBM_STATUS__IH_BUSY_MASK) - reset_mask |= AMDGPU_RESET_IH; - - if (tmp & SRBM_STATUS__SEM_BUSY_MASK) - reset_mask |= AMDGPU_RESET_SEM; - - if (tmp & SRBM_STATUS__GRBM_RQ_PENDING_MASK) - reset_mask |= AMDGPU_RESET_GRBM; - - if (adev->asic_type != CHIP_TOPAZ) { - if (tmp & (SRBM_STATUS__UVD_RQ_PENDING_MASK | -
[PATCH 3/7] drm/amdgpu: clean up asic level reset for CI
Drop soft reset, always use pci config reset. Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/cik.c | 308 +-- 1 file changed, 4 insertions(+), 304 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/cik.c b/drivers/gpu/drm/amd/amdgpu/cik.c index 8265603..2bef867 100644 --- a/drivers/gpu/drm/amd/amdgpu/cik.c +++ b/drivers/gpu/drm/amd/amdgpu/cik.c @@ -1060,257 +1060,6 @@ static int cik_read_register(struct amdgpu_device *adev, u32 se_num, return -EINVAL; } -static void cik_print_gpu_status_regs(struct amdgpu_device *adev) -{ - dev_info(adev->dev, " GRBM_STATUS=0x%08X\n", - RREG32(mmGRBM_STATUS)); - dev_info(adev->dev, " GRBM_STATUS2=0x%08X\n", - RREG32(mmGRBM_STATUS2)); - dev_info(adev->dev, " GRBM_STATUS_SE0=0x%08X\n", - RREG32(mmGRBM_STATUS_SE0)); - dev_info(adev->dev, " GRBM_STATUS_SE1=0x%08X\n", - RREG32(mmGRBM_STATUS_SE1)); - dev_info(adev->dev, " GRBM_STATUS_SE2=0x%08X\n", - RREG32(mmGRBM_STATUS_SE2)); - dev_info(adev->dev, " GRBM_STATUS_SE3=0x%08X\n", - RREG32(mmGRBM_STATUS_SE3)); - dev_info(adev->dev, " SRBM_STATUS=0x%08X\n", - RREG32(mmSRBM_STATUS)); - dev_info(adev->dev, " SRBM_STATUS2=0x%08X\n", - RREG32(mmSRBM_STATUS2)); - dev_info(adev->dev, " SDMA0_STATUS_REG = 0x%08X\n", - RREG32(mmSDMA0_STATUS_REG + SDMA0_REGISTER_OFFSET)); - dev_info(adev->dev, " SDMA1_STATUS_REG = 0x%08X\n", -RREG32(mmSDMA0_STATUS_REG + SDMA1_REGISTER_OFFSET)); - dev_info(adev->dev, " CP_STAT = 0x%08x\n", RREG32(mmCP_STAT)); - dev_info(adev->dev, " CP_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT1)); - dev_info(adev->dev, " CP_STALLED_STAT2 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT2)); - dev_info(adev->dev, " CP_STALLED_STAT3 = 0x%08x\n", -RREG32(mmCP_STALLED_STAT3)); - dev_info(adev->dev, " CP_CPF_BUSY_STAT = 0x%08x\n", -RREG32(mmCP_CPF_BUSY_STAT)); - dev_info(adev->dev, " CP_CPF_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_CPF_STALLED_STAT1)); - dev_info(adev->dev, " CP_CPF_STATUS = 0x%08x\n", RREG32(mmCP_CPF_STATUS)); - dev_info(adev->dev, " CP_CPC_BUSY_STAT = 0x%08x\n", RREG32(mmCP_CPC_BUSY_STAT)); - dev_info(adev->dev, " CP_CPC_STALLED_STAT1 = 0x%08x\n", -RREG32(mmCP_CPC_STALLED_STAT1)); - dev_info(adev->dev, " CP_CPC_STATUS = 0x%08x\n", RREG32(mmCP_CPC_STATUS)); -} - -/** - * cik_gpu_check_soft_reset - check which blocks are busy - * - * @adev: amdgpu_device pointer - * - * Check which blocks are busy and return the relevant reset - * mask to be used by cik_gpu_soft_reset(). - * Returns a mask of the blocks to be reset. - */ -u32 amdgpu_cik_gpu_check_soft_reset(struct amdgpu_device *adev) -{ - u32 reset_mask = 0; - u32 tmp; - - /* GRBM_STATUS */ - tmp = RREG32(mmGRBM_STATUS); - if (tmp & (GRBM_STATUS__PA_BUSY_MASK | GRBM_STATUS__SC_BUSY_MASK | - GRBM_STATUS__BCI_BUSY_MASK | GRBM_STATUS__SX_BUSY_MASK | - GRBM_STATUS__TA_BUSY_MASK | GRBM_STATUS__VGT_BUSY_MASK | - GRBM_STATUS__DB_BUSY_MASK | GRBM_STATUS__CB_BUSY_MASK | - GRBM_STATUS__GDS_BUSY_MASK | GRBM_STATUS__SPI_BUSY_MASK | - GRBM_STATUS__IA_BUSY_MASK | GRBM_STATUS__IA_BUSY_NO_DMA_MASK)) - reset_mask |= AMDGPU_RESET_GFX; - - if (tmp & (GRBM_STATUS__CP_BUSY_MASK | GRBM_STATUS__CP_COHERENCY_BUSY_MASK)) - reset_mask |= AMDGPU_RESET_CP; - - /* GRBM_STATUS2 */ - tmp = RREG32(mmGRBM_STATUS2); - if (tmp & GRBM_STATUS2__RLC_BUSY_MASK) - reset_mask |= AMDGPU_RESET_RLC; - - /* SDMA0_STATUS_REG */ - tmp = RREG32(mmSDMA0_STATUS_REG + SDMA0_REGISTER_OFFSET); - if (!(tmp & SDMA0_STATUS_REG__IDLE_MASK)) - reset_mask |= AMDGPU_RESET_DMA; - - /* SDMA1_STATUS_REG */ - tmp = RREG32(mmSDMA0_STATUS_REG + SDMA1_REGISTER_OFFSET); - if (!(tmp & SDMA0_STATUS_REG__IDLE_MASK)) - reset_mask |= AMDGPU_RESET_DMA1; - - /* SRBM_STATUS2 */ - tmp = RREG32(mmSRBM_STATUS2); - if (tmp & SRBM_STATUS2__SDMA_BUSY_MASK) - reset_mask |= AMDGPU_RESET_DMA; - - if (tmp & SRBM_STATUS2__SDMA1_BUSY_MASK) - reset_mask |= AMDGPU_RESET_DMA1; - - /* SRBM_STATUS */ - tmp = RREG32(mmSRBM_STATUS); - - if (tmp & SRBM_STATUS__IH_BUSY_MASK) - reset_mask |= AMDGPU_RESET_IH; - - if (tmp & SRBM_STATUS__SEM_BUSY_MASK) - reset_mask |= AMDGPU_RESET_SEM; - - if (tmp & SRBM_STATUS__GRBM_RQ_PENDING_MASK) - reset_mask |= AMDGPU_RESET_GRBM; - -
[PATCH 2/7] drm/amdgpu: Add some tweaks to gfx 8 soft reset
Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c | 23 ++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c index 4a6d761..7f5625e 100644 --- a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c +++ b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c @@ -4186,7 +4186,18 @@ static int gfx_v8_0_soft_reset(void *handle) gfx_v8_0_cp_gfx_enable(adev, false); /* Disable MEC parsing/prefetching */ - /* XXX todo */ + gfx_v8_0_cp_compute_enable(adev, false); + + if (grbm_soft_reset || srbm_soft_reset) { + tmp = RREG32(mmGMCON_DEBUG); + tmp = REG_SET_FIELD(tmp, + GMCON_DEBUG, GFX_STALL, 1); + tmp = REG_SET_FIELD(tmp, + GMCON_DEBUG, GFX_CLEAR, 1); + WREG32(mmGMCON_DEBUG, tmp); + + udelay(50); + } if (grbm_soft_reset) { tmp = RREG32(mmGRBM_SOFT_RESET); @@ -4215,6 +4226,16 @@ static int gfx_v8_0_soft_reset(void *handle) WREG32(mmSRBM_SOFT_RESET, tmp); tmp = RREG32(mmSRBM_SOFT_RESET); } + + if (grbm_soft_reset || srbm_soft_reset) { + tmp = RREG32(mmGMCON_DEBUG); + tmp = REG_SET_FIELD(tmp, + GMCON_DEBUG, GFX_STALL, 0); + tmp = REG_SET_FIELD(tmp, + GMCON_DEBUG, GFX_CLEAR, 0); + WREG32(mmGMCON_DEBUG, tmp); + } + /* Wait a little for things to settle down */ udelay(50); gfx_v8_0_print_status((void *)adev); -- 2.5.0
[PATCH 1/7] drm/amdgpu: fix tonga smu resume
Need to make sure smu buffers are pinned on resume. This matches what Fiji does. Cc: stable at vger.kernel.org Reviewed-by: Junwei Zhang Reviewed-by: Christian König Reviewed-by: Ken Wang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/tonga_dpm.c | 17 ++--- 1 file changed, 2 insertions(+), 15 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/tonga_dpm.c b/drivers/gpu/drm/amd/amdgpu/tonga_dpm.c index f4a13465..0497784 100644 --- a/drivers/gpu/drm/amd/amdgpu/tonga_dpm.c +++ b/drivers/gpu/drm/amd/amdgpu/tonga_dpm.c @@ -122,25 +122,12 @@ static int tonga_dpm_hw_fini(void *handle) static int tonga_dpm_suspend(void *handle) { - return 0; + return tonga_dpm_hw_fini(handle); } static int tonga_dpm_resume(void *handle) { - int ret; - struct amdgpu_device *adev = (struct amdgpu_device *)handle; - - mutex_lock(>pm.mutex); - - ret = tonga_smu_start(adev); - if (ret) { - DRM_ERROR("SMU start failed\n"); - goto fail; - } - -fail: - mutex_unlock(>pm.mutex); - return ret; + return tonga_dpm_hw_init(handle); } static int tonga_dpm_set_clockgating_state(void *handle, -- 2.5.0
[PATCH 0/7] Add gpu reset to amdgpu
This patch set gets basic gpu reset working with amdgpu. It's only been tested via debugfs. It still needs to be integrated into the lockup detection in the driver to be used for runtime lockup resets. Alex Deucher (7): drm/amdgpu: fix tonga smu resume drm/amdgpu: Add some tweaks to gfx 8 soft reset drm/amdgpu: clean up asic level reset for CI drm/amdgpu: clean up asic level reset for VI drm/amdgpu: post card after hard reset drm/amdgpu: add a debugfs property to trigger a GPU reset drm/amdgpu: drop hard_reset module parameter drivers/gpu/drm/amd/amdgpu/amdgpu.h| 1 - drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 3 + drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c| 4 - drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c | 20 +- drivers/gpu/drm/amd/amdgpu/cik.c | 308 +-- drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c | 23 +- drivers/gpu/drm/amd/amdgpu/tonga_dpm.c | 17 +- drivers/gpu/drm/amd/amdgpu/vi.c| 385 + 8 files changed, 54 insertions(+), 707 deletions(-) -- 2.5.0
linux-4.4 bisected: kwin5 stuck on kde5 loading screen with radeon
On 01/15/2016 01:26 PM, Ville Syrjälä wrote: > On Fri, Jan 15, 2016 at 11:34:08AM +0100, Vlastimil Babka wrote: >> >> I have suspected that kwin is waiting for some event, but nevertheless >> tried bisecting the kernel between 4.3 and 4.4, which lead to: >> >> # first bad commit: [4dfd64862ff852df7b1198d667dda778715ee88f] drm: Use >> vblank timestamps to guesstimate how many vblanks were missed >> >> I can confirm that 4.4 works if I revert the following commits: >> 63154ff230fc9255cc507af6277cd181943c50a1 "drm/amdgpu: Fixup hw vblank >> counter/ts for new drm_update_vblank_count() (v3)" >> >> d1145ad1e41b6c33758a856163198cb53bb96a50 "drm/radeon: Fixup hw vblank >> counter/ts for new drm_update_vblank_count() (v2)" > > The sha1s don't seem to match what I have, so not sure which kernel tree Hm sorry, I pasted the sha1 of the reverts by mistake. Correct sha1 are: 5b5561b3660db734652fbd02b4b6cbe00434d96b "drm/radeon: Fixup hw vblank counter/ts for new drm_update_vblank_count() (v2)" fa4270d8e0257b4b76f11baa2866f4313d29aaf5 "drm: Don't zero vblank timestamps from the irq handler" 235fabe09b46469adad2c9e4cb0563758155187c "drm: Add DRM_DEBUG_VBL()" 4dfd64862ff852df7b1198d667dda778715ee88f "drm: Use vblank timestamps to guesstimate how many vblanks were missed" 8e36f9d33c134d5c6448ad65b423a9fd94e045cf "drm/amdgpu: Fixup hw vblank counter/ts for new drm_update_vblank_count() (v3)" Also, it turns out that the process actually showing the progress is "ksplashqml", not kwin. It survives killing kwin, and restarting kwin just makes it shown on top again, or something. If I force kill ksplashqml instead of kwin, the desktop works including decorations and everything. ksplashqml itself also waits in kernel in poll(). I'll try some of your suggestions, thanks!
[PATCH v3 1/3] drm: add generic zpos property
On Fri, Jan 15, 2016 at 11:12:25AM +0100, Daniel Vetter wrote: > On Fri, Jan 15, 2016 at 10:09:14AM +0100, Marek Szyprowski wrote: > > Hello, > > > > On 2016-01-14 11:46, Ville Syrjälä wrote: > > >On Tue, Jan 12, 2016 at 02:39:18PM +0100, Marek Szyprowski wrote: > > >>This patch adds support for generic plane's zpos property property with > > >>well-defined semantics: > > >>- added zpos properties to drm core and plane state structures > > >>- added helpers for normalizing zpos properties of given set of planes > > >>- well defined semantics: planes are sorted by zpos values and then plane > > >> id value if zpos equals > > >> > > >>Normalized zpos values are calculated automatically when generic > > >>muttable zpos property has been initialized. Drivers can simply use > > >>plane_state->normalized_zpos in their atomic_check and/or plane_update > > >>callbacks without any additional calls to DRM core. > > >> > > >>Signed-off-by: Marek Szyprowski > > >>--- > > >> Documentation/DocBook/gpu.tmpl | 14 - > > >> drivers/gpu/drm/drm_atomic.c| 4 ++ > > >> drivers/gpu/drm/drm_atomic_helper.c | 116 > > >> > > >> drivers/gpu/drm/drm_crtc.c | 53 > > >> include/drm/drm_crtc.h | 14 + > > >> 5 files changed, 199 insertions(+), 2 deletions(-) > > >> > > >>diff --git a/Documentation/DocBook/gpu.tmpl > > >>b/Documentation/DocBook/gpu.tmpl > > >>index 6c6e81a9eaf4..f6b7236141b6 100644 > > >>--- a/Documentation/DocBook/gpu.tmpl > > >>+++ b/Documentation/DocBook/gpu.tmpl > > >>@@ -2004,7 +2004,7 @@ void intel_crt_init(struct drm_device *dev) > > >> Description/Restrictions > > >> > > >> > > >>- DRM > > >>+ DRM > > >> Generic > > >> ârotationâ > > >> BITMASK > > >>@@ -2256,7 +2256,7 @@ void intel_crt_init(struct drm_device *dev) > > >> property to suggest an Y offset for a > > >> connector > > >> > > >> > > >>- Optional > > >>+ Optional > > >> âscaling modeâ > > >> ENUM > > >> { "None", "Full", "Center", "Full aspect" > > >> } > > >>@@ -2280,6 +2280,16 @@ void intel_crt_init(struct drm_device *dev) > > >> TBD > > >> > > >> > > >>+ "zpos" > > >>+ RANGE > > >>+ Min=0, Max=255 > > >>+ Plane > > >>+ Plane's 'z' position during blending (0 for > > >>background, 255 for frontmost). > > >>+ If two planes assigned to same CRTC have equal zpos values, the > > >>plane with higher plane > > >>+ id is treated as closer to front. Can be IMMUTABLE if driver > > >>doesn't support changing > > >>+ planes' order. > > >I don't think this is going to work very well. Mixing the same range > > >of 0-255 for all planes, with potentially some of them being > > >IMMUTABLE for sure won't end well, or at least won't allow userspace to > > >see if there are any constraints between the zpos of the planes. > > > > > >So I think what we should do is let the driver specify the valid range, > > >and get rid of the obj id based conflict resolution in favor of just > > >rejecting conflicts outright. In cases where you can't move the planes > > >between crtcs, the driver ought to specify the range based on the > > >number of planes present on the crtc. If planes can be moved betweens > > >crtcs the range obviously needs to be larger to accomodate all the > > >possible planes on the crtc. > > > > > >Eg. on Intel VLV/CHV we could have the following setup: > > >primary zpos 0-2 > > >sprite 0 zpos 0-2 > > >sprite 1 zpos 0-2 > > >cursor zpos 3 > > > > > >That makes it very clear the curso is always on top, and the other > > >planes can be rearranged more or less freely. These planes can't be > > >moved between crtcs, so each there's an identical set of planes for > > >each crtc. > > > > > >On old Intel hw (gen2/3) we could have something like: > > >plane A zpos 0-3 > > >plane B zpos 0-3 > > >plane C zpos 0-3 > > >overlay zpos 0-3 > > >cursor B zpos 4 > > >cursor A zpos 5 > > > > > >Most of these planes can be moved between crtcs, and IIRC there > > >are probably more constraints on exactly how they can be stacked, but > > >this is at least fairly close to the truth. Again the cursors are always > > >on top, and in this case the order between the two cursor planes is also > > >fixed. > > > > I wasn't aware of a hardware, which has limited configuration of zpos only > > to some planes. I thought only about 2 cases: either completely configurable > > planes arrangement, or planes fixed to some hw dependent order. I see no > > problem to let drivers to define their own limits for mutable zpos property. > > > > Now the question is weather we should allow to set the non-zero minimal > > value > > for mutable zpos? I can imagine that there might be a hardware, which has > > fixed background plane and a few configurable overlay planes. I assume that > > in such case, the
[Bug 106901] Brightness / WIFI Key does not generate any events
https://bugzilla.kernel.org/show_bug.cgi?id=106901 --- Comment #28 from Roman Gruber --- lsmod Module Size Used by nvidia_modeset721045 3 nvidia 9922734 59 nvidia_modeset intel_powerclamp7094 0 xhci_pci3818 0 xhci_hcd 86326 1 xhci_pci drm 238337 3 nvidia iTCO_wdt5540 0 ehci_pci3679 0 iTCO_vendor_support 1960 1 iTCO_wdt ehci_hcd 35048 1 ehci_pci pcspkr 2035 0 input_leds 2894 0 Newest binary nvidia-driver in use ASUS-G75VW roman # qlist -Iv nvidia-drivers x11-drivers/nvidia-drivers-361.18 -- You are receiving this mail because: You are watching the assignee of the bug.
[Bug 106901] Brightness / WIFI Key does not generate any events
https://bugzilla.kernel.org/show_bug.cgi?id=106901 --- Comment #27 from Roman Gruber --- Linux ASUS-G75VW 4.4.0-gentoo_14-01-2016 #1 SMP Thu Jan 14 19:15:47 CET 2016 x86_64 Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz GenuineIntel GNU/Linux same behaviour -- You are receiving this mail because: You are watching the assignee of the bug.
[Bug 106901] Brightness / WIFI Key does not generate any events
https://bugzilla.kernel.org/show_bug.cgi?id=106901 Roman Gruber changed: What|Removed |Added Kernel Version|Linux ASUS-G75VW|Linux ASUS-G75VW |4.3.3-gentoo_2015-12-17 #1 |4.4.0-gentoo_14-01-2016 #1 |SMP Thu Dec 17 16:28:50 CET |SMP Thu Jan 14 19:15:47 CET |2015 x86_64 Intel(R)|2016 x86_64 Intel(R) |Core(TM) i7-3610QM CPU @|Core(TM) i7-3610QM CPU @ |2.30GHz GenuineIntel|2.30GHz GenuineIntel |GNU/Linux |GNU/Linux -- You are receiving this mail because: You are watching the assignee of the bug.
[Bug 106901] Brightness / WIFI Key does not generate any events
https://bugzilla.kernel.org/show_bug.cgi?id=106901 --- Comment #26 from Roman Gruber --- uname -a; echo " ";dmesg |grep ACPI Linux ASUS-G75VW 4.4.0-gentoo_14-01-2016 #1 SMP Thu Jan 14 19:15:47 CET 2016 x86_64 Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz GenuineIntel GNU/Linux [0.00] BIOS-e820: [mem 0xdd6ab000-0xddcabfff] ACPI NVS [0.00] BIOS-e820: [mem 0xde586000-0xde805fff] ACPI NVS [0.00] BIOS-e820: [mem 0xde806000-0xde80afff] ACPI data [0.00] BIOS-e820: [mem 0xde80c000-0xde84efff] ACPI NVS [0.00] efi: ACPI=0xde7de000 ACPI 2.0=0xde7de000 SMBIOS=0xde084398 [0.00] ACPI: Early table checksum verification disabled [0.00] ACPI: RSDP 0xDE7DE000 24 (v02 _ASUS_) [0.00] ACPI: XSDT 0xDE7DE080 84 (v01 _ASUS_ Notebook 01072009 AMI 00010013) [0.00] ACPI: FACP 0xDE7EE9B8 00010C (v05 _ASUS_ Notebook 01072009 AMI 00010013) [0.00] ACPI: DSDT 0xDE7DE190 010828 (v02 _ASUS_ Notebook 0013 INTL 20091112) [0.00] ACPI: FACS 0xDE803080 40 [0.00] ACPI: APIC 0xDE7EEAC8 92 (v03 _ASUS_ Notebook 01072009 AMI 00010013) [0.00] ACPI: FPDT 0xDE7EEB60 44 (v01 _ASUS_ Notebook 01072009 AMI 00010013) [0.00] ACPI: ECDT 0xDE7EEBA8 C1 (v01 _ASUS_ Notebook 01072009 AMI. 0005) [0.00] ACPI: MCFG 0xDE7EEC70 3C (v01 _ASUS_ Notebook 01072009 MSFT 0097) [0.00] ACPI: HPET 0xDE7EECB0 38 (v01 _ASUS_ Notebook 01072009 AMI. 0005) [0.00] ACPI: SSDT 0xDE7EECE8 00066E (v01 AhciR1 AhciTab1 1000 INTL 20091112) [0.00] ACPI: SSDT 0xDE7EF358 00049E (v01 AhciR2 AhciTab2 1000 INTL 20091112) [0.00] ACPI: SSDT 0xDE7EF7F8 00090A (v01 PmRef Cpu0Ist 3000 INTL 20051117) [0.00] ACPI: SSDT 0xDE7F0108 000A92 (v01 PmRef CpuPm 3000 INTL 20051117) [0.00] ACPI: BGRT 0xDE7F0BA0 38 (v00 _ASUS_ Notebook 01072009 ASUS 00010013) [0.00] ACPI: MSDM 0xDE585E18 55 (v03 _ASUS_ Notebook ASUS 0001) [0.00] ACPI: Local APIC address 0xfee0 [0.00] ACPI: PM-Timer IO Port: 0x408 [0.00] ACPI: Local APIC address 0xfee0 [0.00] ACPI: LAPIC_NMI (acpi_id[0xff] high edge lint[0x1]) [0.00] ACPI: INT_SRC_OVR (bus 0 bus_irq 0 global_irq 2 dfl dfl) [0.00] ACPI: INT_SRC_OVR (bus 0 bus_irq 9 global_irq 9 high level) [0.00] ACPI: IRQ0 used by override. [0.00] ACPI: IRQ9 used by override. [0.00] Using ACPI (MADT) for SMP configuration information [0.00] ACPI: HPET id: 0x8086a701 base: 0xfed0 [0.31] ACPI: Core revision 20150930 [0.018220] ACPI: 5 ACPI AML tables successfully acquired and loaded [0.158269] PM: Registering ACPI NVS region [mem 0xdd6ab000-0xddcabfff] (6295552 bytes) [0.158430] PM: Registering ACPI NVS region [mem 0xde586000-0xde805fff] (2621440 bytes) [0.158502] PM: Registering ACPI NVS region [mem 0xde80c000-0xde84efff] (274432 bytes) [0.311679] ACPI FADT declares the system doesn't support PCIe ASPM, so disable it [0.311690] ACPI: bus type PCI registered [1.331723] ACPI: Added _OSI(Module Device) [1.331734] ACPI: Added _OSI(Processor Device) [1.331745] ACPI: Added _OSI(3.0 _SCP Extensions) [1.331755] ACPI: Added _OSI(Processor Aggregator Device) [1.333954] ACPI : EC: EC description table is found, configuring boot EC [1.333977] ACPI : EC: EC started [1.336121] ACPI: Executed 1 blocks of module-level executable AML code [1.341939] [Firmware Bug]: ACPI: BIOS _OSI(Linux) query ignored [1.342599] ACPI: Dynamic OEM Table Load: [1.342618] ACPI: SSDT 0x88040E15B000 000853 (v01 PmRef Cpu0Cst 3001 INTL 20051117) [1.343557] ACPI: Dynamic OEM Table Load: [1.343573] ACPI: SSDT 0x88040D89E400 000303 (v01 PmRef ApIst 3000 INTL 20051117) [1.344377] ACPI: Dynamic OEM Table Load: [1.344392] ACPI: SSDT 0x88041E433E00 000119 (v01 PmRef ApCst 3000 INTL 20051117) [1.347118] ACPI: Interpreter enabled [1.347136] ACPI Exception: AE_NOT_FOUND, While evaluating Sleep State [\_S1_] (20150930/hwxface-580) [1.347152] ACPI Exception: AE_NOT_FOUND, While evaluating Sleep State [\_S2_] (20150930/hwxface-580) [1.347180] ACPI: (supports S0 S3 S4 S5) [1.347190] ACPI: Using IOAPIC for interrupt routing [1.347238] PCI: Using host bridge windows from ACPI; if necessary, use "pci=nocrs" and report a bug [1.357145] ACPI: PCI Root Bridge [PCI0] (domain [bus 00-3e]) [1.358371] pci :00:01.0: System wakeup disabled by ACPI [1.358626] pci :00:14.0: System wakeup disabled by ACPI [1.359092] pci :00:1a.0: System wakeup disabled by ACPI [1.359322] pci :00:1b.0: System wakeup disabled by ACPI [1.359539] pci
[PATCH] configure.ac: disable annoying warning -Wmissing-field-initializers
On 12 January 2016 at 23:14, Marek Olšák wrote: > From: Marek Olšák > > It warns for all "{}" initializers. Well, I want us to use {}. > --- > configure.ac | 3 ++- > intel/intel_decode.c | 2 -- The whole of libdrm, minus the intel_decode can get away without using such constructs. And yes that includes radeon and amdgpu. NACK on this one - please be consistent with existing code base. -Emil
[PATCH] drm: nouveau: fix nouveau_debugfs_init prototype
> Emil Velikov hat am 15. Januar 2016 um 12:06 > geschrieben: > > On 13 January 2016 at 16:00, Arnd Bergmann wrote: > > On Wednesday 13 January 2016 14:55:47 Karol Herbst wrote: > >> > Arnd Bergmann hat am 13. Januar 2016 um 14:48 > >> > geschrieben: > >> > > >> > The new debugfs initialization code fails to build when CONFIG_DEBUG_FS > >> > is disabled: > >> > > >> > In file included from > >> > /git/arm-soc/drivers/gpu/drm/nouveau/nouveau_drm.c:57:0: > >> > drivers/gpu/drm/nouveau/nouveau_debugfs.h: In function > >> > 'nouveau_debugfs_init': > >> > drivers/gpu/drm/nouveau/nouveau_debugfs.h:37:29: error: parameter name > >> > omitted > >> > nouveau_debugfs_init(struct nouveau_drm *) > >> > > >> > This fixes the prototypes so we can build it again. > >> > > >> > >> thanks for this. I already send a patch to the nouveau ML here: > >> http://lists.freedesktop.org/archives/nouveau/2016-January/023779.html > > > > Ok, thanks > > > Fwiw Arnd's fix feels a lot better - it lacks typos, has a fixes tag, > comprehensive commit message etc. etc. :-) > > -Emil no worries, I am still learning after all Karol
[PATCH] drm: nouveau: fix nouveau_debugfs_init prototype
On 13 January 2016 at 16:00, Arnd Bergmann wrote: > On Wednesday 13 January 2016 14:55:47 Karol Herbst wrote: >> > Arnd Bergmann hat am 13. Januar 2016 um 14:48 >> > geschrieben: >> > >> > The new debugfs initialization code fails to build when CONFIG_DEBUG_FS >> > is disabled: >> > >> > In file included from >> > /git/arm-soc/drivers/gpu/drm/nouveau/nouveau_drm.c:57:0: >> > drivers/gpu/drm/nouveau/nouveau_debugfs.h: In function >> > 'nouveau_debugfs_init': >> > drivers/gpu/drm/nouveau/nouveau_debugfs.h:37:29: error: parameter name >> > omitted >> > nouveau_debugfs_init(struct nouveau_drm *) >> > >> > This fixes the prototypes so we can build it again. >> > >> >> thanks for this. I already send a patch to the nouveau ML here: >> http://lists.freedesktop.org/archives/nouveau/2016-January/023779.html > > Ok, thanks > Fwiw Arnd's fix feels a lot better - it lacks typos, has a fixes tag, comprehensive commit message etc. etc. :-) -Emil
[Bug 77835] X crash when using xrandr with R9 290X and 7870 for triple head
https://bugs.freedesktop.org/show_bug.cgi?id=77835 --- Comment #7 from Maik Broemme --- I can't reproduce it anymore as I don't have the cards anymore. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/a5476939/attachment.html>
[RFC 29/29] dma-buf/fence: de-stage sync framework
From: Gustavo PadovanThe sync framework is ready for mainline inclusion. Here we move it to drivers/dma-buf and the header files to the appropiated places. The sync framework contained some abstractions around struct fence and those were removed in the de-staging process among other changes: Userspace visible changes - * The sw_sync file was moved from /dev/sw_sync to /sync/sw_sync. No other change. Kernel API changes -- * struct sync_timeline is now struct fence_timeline * sync_timeline_ops is now fence_timeline_ops and they now carry struct fence as parameter instead of struct sync_pt * a .cleanup() fence op was added to allow sync_fence to run a cleanup when the fence_timeline is destroyed * added fence_add_used_data() to pass a private point to struct fence. This pointer is sent back on the .cleanup op. * The sync timeline function were moved to be fence_timeline functions: - sync_timeline_create() -> fence_timeline_create() - sync_timeline_get() -> fence_timeline_get() - sync_timeline_put() -> fence_timeline_put() - sync_timeline_destroy() -> fence_timeline_destroy() - sync_timeline_signal() -> fence_timeline_signal() * sync_pt_create() was replaced be fence_create_on_timeline() Internal changes * fence_timeline_ops was removed in favor of direct use fence_ops * fence default functions were created for fence_ops * removed structs sync_pt, sw_sync_timeline and sw_sync_pt Signed-off-by: Gustavo Padovan --- drivers/Kconfig| 2 ++ drivers/dma-buf/Kconfig| 22 ++ drivers/dma-buf/Makefile | 2 ++ drivers/{staging/android => dma-buf}/sw_sync.c | 3 +-- drivers/{staging/android => dma-buf}/sync.c| 7 --- drivers/{staging/android => dma-buf}/sync_debug.c | 2 +- drivers/staging/android/Kconfig| 19 --- drivers/staging/android/Makefile | 2 -- .../staging/android => include/linux}/sw_sync.h| 4 ++-- {drivers/staging/android => include/linux}/sync.h | 4 ++-- .../android/trace => include/trace/events}/sync.h | 5 ++--- .../android/uapi => include/uapi/linux}/sw_sync.h | 0 .../android/uapi => include/uapi/linux}/sync.h | 0 13 files changed, 38 insertions(+), 34 deletions(-) create mode 100644 drivers/dma-buf/Kconfig rename drivers/{staging/android => dma-buf}/sw_sync.c (98%) rename drivers/{staging/android => dma-buf}/sync.c (99%) rename drivers/{staging/android => dma-buf}/sync_debug.c (99%) rename {drivers/staging/android => include/linux}/sw_sync.h (95%) rename {drivers/staging/android => include/linux}/sync.h (99%) rename {drivers/staging/android/trace => include/trace/events}/sync.h (92%) rename {drivers/staging/android/uapi => include/uapi/linux}/sw_sync.h (100%) rename {drivers/staging/android/uapi => include/uapi/linux}/sync.h (100%) diff --git a/drivers/Kconfig b/drivers/Kconfig index d2ac339..430f761 100644 --- a/drivers/Kconfig +++ b/drivers/Kconfig @@ -114,6 +114,8 @@ source "drivers/rtc/Kconfig" source "drivers/dma/Kconfig" +source "drivers/dma-buf/Kconfig" + source "drivers/dca/Kconfig" source "drivers/auxdisplay/Kconfig" diff --git a/drivers/dma-buf/Kconfig b/drivers/dma-buf/Kconfig new file mode 100644 index 000..4168f89 --- /dev/null +++ b/drivers/dma-buf/Kconfig @@ -0,0 +1,22 @@ +menu "DMABUF options" + +config SYNC + bool "Synchronization framework" + default n + select ANON_INODES + select DMA_SHARED_BUFFER + ---help--- + This option enables the framework for synchronization between multiple + drivers. Sync implementations can take advantage of hardware + synchronization built into devices like GPUs. + +config SW_SYNC + bool "Software synchronization objects" + default n + depends on SYNC + ---help--- + A sync object driver that uses a 32bit counter to coordinate + synchronization. Useful when there is no hardware primitive backing + the synchronization. + +endmenu diff --git a/drivers/dma-buf/Makefile b/drivers/dma-buf/Makefile index fb03696..b870923 100644 --- a/drivers/dma-buf/Makefile +++ b/drivers/dma-buf/Makefile @@ -1 +1,3 @@ obj-y := dma-buf.o fence.o fence_debug.o reservation.o seqno-fence.o +obj-$(CONFIG_SYNC) += sync.o sync_debug.o +obj-$(CONFIG_SW_SYNC) += sw_sync.o diff --git a/drivers/staging/android/sw_sync.c b/drivers/dma-buf/sw_sync.c similarity index 98% rename from drivers/staging/android/sw_sync.c rename to drivers/dma-buf/sw_sync.c index 8c83bad..32d0800 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/dma-buf/sw_sync.c @@ -22,8 +22,7 @@ #include #include #include - -#include "sw_sync.h" +#include
[RFC 28/29] staging/android: use .cleanup() to interrupt any sync_fence waiter
From: Gustavo PadovanWhen the timeline is being destroyed all the waiters waiting for the sync_fence to signal need to be woken up and finished as well. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sw_sync.c | 8 drivers/staging/android/sync.c| 9 + drivers/staging/android/sync.h| 2 ++ 3 files changed, 19 insertions(+) diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index ee7a942..8c83bad 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -25,6 +25,13 @@ #include "sw_sync.h" +static void sw_sync_cleanup(struct fence *fence, void *user_data) +{ + struct sync_fence *sync_fence = user_data; + + sync_fence_cleanup(sync_fence); +} + static const struct fence_ops sw_sync_fence_ops = { .get_driver_name = fence_default_get_driver_name, .get_timeline_name = fence_default_get_timeline_name, @@ -32,6 +39,7 @@ static const struct fence_ops sw_sync_fence_ops = { .signaled = fence_default_signaled, .wait = fence_default_wait, .release = fence_default_release, + .cleanup = sw_sync_cleanup, .fill_driver_data = fence_default_fill_driver_data, .fence_value_str = fence_default_value_str, .timeline_value_str = fence_default_timeline_value_str, diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 956b4e9..aafecf4 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -91,6 +91,8 @@ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *fence) sync_fence_debug_add(sync_fence); + fence_add_user_data(fence, sync_fence); + return sync_fence; } EXPORT_SYMBOL(sync_fence_create_dma); @@ -101,6 +103,13 @@ struct sync_fence *sync_fence_create(const char *name, struct fence *fence) } EXPORT_SYMBOL(sync_fence_create); +void sync_fence_cleanup(struct sync_fence *sync_fence) +{ + atomic_set(_fence->status, -ENOENT); + wake_up_all(_fence->wq); +} +EXPORT_SYMBOL(sync_fence_cleanup); + struct sync_fence *sync_fence_fdget(int fd) { struct file *file = fget(fd); diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index 8e6827b..d60d9c2 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -98,6 +98,8 @@ struct sync_fence *sync_fence_create(const char *name, struct fence *fence); */ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt); +void sync_fence_cleanup(struct sync_fence *sync_fence); + /* * API for sync_fence consumers */ -- 2.5.0
[RFC 27/29] dma-buf/fence: add .cleanup() callback
From: Gustavo PadovanCalled when the fence_timeline is destroyed so users can cleanup routines on fences. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 24 include/linux/fence.h | 4 2 files changed, 28 insertions(+) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 26f5f0f..3973b35 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -140,6 +140,9 @@ EXPORT_SYMBOL(fence_timeline_put); */ void fence_timeline_destroy(struct fence_timeline *timeline) { + unsigned long flags; + struct fence *fence, *next; + timeline->destroyed = true; /* * Ensure timeline is marked as destroyed before @@ -147,6 +150,15 @@ void fence_timeline_destroy(struct fence_timeline *timeline) */ smp_wmb(); + spin_lock_irqsave(>lock, flags); + list_for_each_entry_safe(fence, next, >active_list_head, +active_list) { + if (fence->ops->cleanup) + fence->ops->cleanup(fence, fence->priv); + list_del_init(>active_list); + } + spin_unlock_irqrestore(>lock, flags); + fence_timeline_put(timeline); } EXPORT_SYMBOL(fence_timeline_destroy); @@ -839,3 +851,15 @@ fence_init(struct fence *fence, const struct fence_ops *ops, trace_fence_init(fence); } EXPORT_SYMBOL(fence_init); + +/** + * fence_add_user_data - add private user data + * @fence: [in]the fence to use + * @user_data: [in]the private data to store + * + * This function adds a private user data point to struct fence. + */ +void fence_add_user_data(struct fence *fence, void *user_data) +{ + fence->priv = user_data; +} diff --git a/include/linux/fence.h b/include/linux/fence.h index 32a26ab..59eabe3 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -116,6 +116,7 @@ struct fence { int status; struct list_head child_list; struct list_head active_list; + void *priv; }; enum fence_flag_bits { @@ -146,6 +147,7 @@ struct fence_cb { * @enable_signaling: enable software signaling of fence. * @signaled: [optional] peek whether the fence is signaled, can be null. * @wait: custom wait implementation, or fence_default_wait. + * @cleanup: [optional] called when the timeline is destroyed * @release: [optional] called on destruction of fence, can be null * @fill_driver_data: [optional] callback to fill in free-form debug info * Returns amount of bytes filled, or -errno. @@ -205,6 +207,7 @@ struct fence_ops { bool (*enable_signaling)(struct fence *fence); bool (*signaled)(struct fence *fence); signed long (*wait)(struct fence *fence, bool intr, signed long timeout); + void (*cleanup)(struct fence *fence, void *user_data); void (*release)(struct fence *fence); int (*fill_driver_data)(struct fence *fence, void *data, int size); @@ -217,6 +220,7 @@ struct fence *fence_create_on_timeline(struct fence_timeline *obj, unsigned int value); void fence_init(struct fence *fence, const struct fence_ops *ops, spinlock_t *lock, unsigned context, unsigned seqno); +void fence_add_user_data(struct fence *fence, void *user_data); void fence_release(struct kref *kref); void fence_free(struct fence *fence); -- 2.5.0
[RFC 26/29] dma-buf/fence: remove pointless fence_timeline_signal at destroy phase
From: Gustavo PadovanAll changes to timeline value come through the user via fence_timeline_signal() calls. When fence_timeline_destroy() is called no changes on timeline->value happens hence call fence_timeline_signal() with no increment is pointless. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 6 +- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 7a5fc9b..26f5f0f 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -136,7 +136,7 @@ EXPORT_SYMBOL(fence_timeline_put); * fence_timeline_destroy - destroy a fence_timeline * @timeline [in]the fence_timeline to destroy * - * This function destroys a timeline. It signals any active fence first. + * This function destroys a timeline. */ void fence_timeline_destroy(struct fence_timeline *timeline) { @@ -147,10 +147,6 @@ void fence_timeline_destroy(struct fence_timeline *timeline) */ smp_wmb(); - /* -* signal any children that their parent is going away. -*/ - fence_timeline_signal(timeline, 0); fence_timeline_put(timeline); } EXPORT_SYMBOL(fence_timeline_destroy); -- 2.5.0
[RFC 25/29] dma-buf/fence: remove unused var from fence_timeline_signal()
From: Gustavo Padovansignaled_pts is not used in this function. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 09faf2e..7a5fc9b 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -166,7 +166,6 @@ EXPORT_SYMBOL(fence_timeline_destroy); void fence_timeline_signal(struct fence_timeline *timeline, unsigned int inc) { unsigned long flags; - LIST_HEAD(signaled_pts); struct fence *fence, *next; spin_lock_irqsave(>lock, flags); -- 2.5.0
[RFC 24/29] dma-buf/fence: add debug to fence timeline
From: Gustavo PadovanBring the debug information that belonged to sync_timeline and sync_pt back. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/Makefile | 2 +- drivers/dma-buf/fence.c | 4 ++ drivers/dma-buf/fence_debug.c| 128 +++ drivers/staging/android/sync.h | 4 -- drivers/staging/android/sync_debug.c | 105 +--- include/linux/fence.h| 18 + 6 files changed, 154 insertions(+), 107 deletions(-) create mode 100644 drivers/dma-buf/fence_debug.c diff --git a/drivers/dma-buf/Makefile b/drivers/dma-buf/Makefile index 57a675f..fb03696 100644 --- a/drivers/dma-buf/Makefile +++ b/drivers/dma-buf/Makefile @@ -1 +1 @@ -obj-y := dma-buf.o fence.o reservation.o seqno-fence.o +obj-y := dma-buf.o fence.o fence_debug.o reservation.o seqno-fence.o diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 0a07fcb..09faf2e 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -84,6 +84,8 @@ struct fence_timeline *fence_timeline_create(unsigned num, int size, INIT_LIST_HEAD(>active_list_head); spin_lock_init(>lock); + fence_timeline_debug_add(timeline); + return timeline; } EXPORT_SYMBOL(fence_timeline_create); @@ -100,6 +102,8 @@ static void fence_timeline_free(struct kref *kref) struct fence_timeline *timeline = container_of(kref, struct fence_timeline, kref); + fence_timeline_debug_remove(timeline); + kfree(timeline); } diff --git a/drivers/dma-buf/fence_debug.c b/drivers/dma-buf/fence_debug.c new file mode 100644 index 000..c7529c6 --- /dev/null +++ b/drivers/dma-buf/fence_debug.c @@ -0,0 +1,128 @@ +/* + * drivers/dma-buf/fence_debug.c + * + * Copyright (C) 2012 Google, Inc. + * + * 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 + +#ifdef CONFIG_DEBUG_FS + +static LIST_HEAD(fence_timeline_list_head); +static DEFINE_SPINLOCK(fence_timeline_list_lock); + +void fence_timeline_debug_add(struct fence_timeline *obj) +{ + unsigned long flags; + + spin_lock_irqsave(_timeline_list_lock, flags); + list_add_tail(>fence_timeline_list, _timeline_list_head); + spin_unlock_irqrestore(_timeline_list_lock, flags); +} +EXPORT_SYMBOL(fence_timeline_debug_add); + +void fence_timeline_debug_remove(struct fence_timeline *obj) +{ + unsigned long flags; + + spin_lock_irqsave(_timeline_list_lock, flags); + list_del(>fence_timeline_list); + spin_unlock_irqrestore(_timeline_list_lock, flags); +} +EXPORT_SYMBOL(fence_timeline_debug_remove); + +const char *fence_status_str(int status) +{ + if (status == 0) + return "signaled"; + + if (status > 0) + return "active"; + + return "error"; +} +EXPORT_SYMBOL(fence_status_str); + +void fence_print(struct seq_file *s, struct fence *fence, bool show) +{ + int status = 1; + struct fence_timeline *parent = fence_parent(fence); + + if (fence_is_signaled_locked(fence)) + status = fence->status; + + seq_printf(s, " %s%sfence %s", + show ? parent->name : "", + show ? "_" : "", + fence_status_str(status)); + + if (status <= 0) { + struct timespec64 ts64 = + ktime_to_timespec64(fence->timestamp); + + seq_printf(s, "@%lld.%09ld", (s64)ts64.tv_sec, ts64.tv_nsec); + } + + if (fence->ops->timeline_value_str && + fence->ops->fence_value_str) { + char value[64]; + + fence->ops->fence_value_str(fence, value, sizeof(value)); + seq_printf(s, ": %s", value); + if (show) { + fence->ops->timeline_value_str(fence, value, + sizeof(value)); + seq_printf(s, " / %s", value); + } + } + + seq_puts(s, "\n"); +} +EXPORT_SYMBOL(fence_print); + +void fence_timeline_print(struct seq_file *s, struct fence_timeline *obj) +{ + struct list_head *pos; + unsigned long flags; + + seq_printf(s, "%s %s: %u\n", obj->name, obj->drv_name, obj->value); + + spin_lock_irqsave(>lock, flags); + list_for_each(pos, >child_list_head) { + struct fence *fence = + container_of(pos, struct fence, child_list); + fence_print(s, fence, false);
[RFC 23/29] staging/android: remove sw_sync_timeline and sw_sync_pt
From: Gustavo PadovanAs we moved value storage to fence_timeline and fence those two structs became useless and can be removed now. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sw_sync.c| 15 ++- drivers/staging/android/sw_sync.h| 24 ++-- drivers/staging/android/sync_debug.c | 12 ++-- 3 files changed, 18 insertions(+), 33 deletions(-) diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index 7250f1b..ee7a942 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -37,25 +37,22 @@ static const struct fence_ops sw_sync_fence_ops = { .timeline_value_str = fence_default_timeline_value_str, }; -struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) +struct fence *sw_sync_pt_create(struct fence_timeline *obj, u32 value) { - return fence_create_on_timeline(>obj, _sync_fence_ops, + return fence_create_on_timeline(obj, _sync_fence_ops, sizeof(struct fence), value); } EXPORT_SYMBOL(sw_sync_pt_create); -struct sw_sync_timeline *sw_sync_timeline_create(const char *name) +struct fence_timeline *sw_sync_timeline_create(const char *name) { - struct sw_sync_timeline *obj = (struct sw_sync_timeline *) - fence_timeline_create(1, sizeof(struct sw_sync_timeline), + return fence_timeline_create(1, sizeof(struct fence_timeline), "sw_sync", name); - - return obj; } EXPORT_SYMBOL(sw_sync_timeline_create); -void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc) +void sw_sync_timeline_inc(struct fence_timeline *obj, u32 inc) { - fence_timeline_signal(>obj, inc); + fence_timeline_signal(obj, inc); } EXPORT_SYMBOL(sw_sync_timeline_inc); diff --git a/drivers/staging/android/sw_sync.h b/drivers/staging/android/sw_sync.h index 85ef780..f912888 100644 --- a/drivers/staging/android/sw_sync.h +++ b/drivers/staging/android/sw_sync.h @@ -22,34 +22,22 @@ #include "sync.h" #include "uapi/sw_sync.h" -struct sw_sync_timeline { - struct fence_timeline obj; - - u32 value; -}; - -struct sw_sync_pt { - struct fencept; - - u32 value; -}; - #if IS_ENABLED(CONFIG_SW_SYNC) -struct sw_sync_timeline *sw_sync_timeline_create(const char *name); -void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc); +struct fence_timeline *sw_sync_timeline_create(const char *name); +void sw_sync_timeline_inc(struct fence_timeline *obj, u32 inc); -struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value); +struct fence *sw_sync_pt_create(struct fence_timeline *obj, u32 value); #else -static inline struct sw_sync_timeline *sw_sync_timeline_create(const char *name) +static inline struct fence_timeline *sw_sync_timeline_create(const char *name) { return NULL; } -static inline void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc) +static inline void sw_sync_timeline_inc(struct fence_timeline *obj, u32 inc) { } -static inline struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, +static inline struct fence *sw_sync_pt_create(struct fence_timeline *obj, u32 value) { return NULL; diff --git a/drivers/staging/android/sync_debug.c b/drivers/staging/android/sync_debug.c index 89b334c..13d225f 100644 --- a/drivers/staging/android/sync_debug.c +++ b/drivers/staging/android/sync_debug.c @@ -225,7 +225,7 @@ static const struct file_operations sync_info_debugfs_fops = { /* opening sw_sync create a new sync obj */ static int sw_sync_debugfs_open(struct inode *inode, struct file *file) { - struct sw_sync_timeline *obj; + struct fence_timeline *obj; char task_comm[TASK_COMM_LEN]; get_task_comm(task_comm, current); @@ -241,13 +241,13 @@ static int sw_sync_debugfs_open(struct inode *inode, struct file *file) static int sw_sync_debugfs_release(struct inode *inode, struct file *file) { - struct sw_sync_timeline *obj = file->private_data; + struct fence_timeline *obj = file->private_data; - fence_timeline_destroy(>obj); + fence_timeline_destroy(obj); return 0; } -static long sw_sync_ioctl_create_fence(struct sw_sync_timeline *obj, +static long sw_sync_ioctl_create_fence(struct fence_timeline *obj, unsigned long arg) { int fd = get_unused_fd_flags(O_CLOEXEC); @@ -294,7 +294,7 @@ err: return err; } -static long sw_sync_ioctl_inc(struct sw_sync_timeline *obj, unsigned long arg) +static long sw_sync_ioctl_inc(struct fence_timeline *obj, unsigned long arg) { u32 value; @@ -309,7 +309,7 @@ static long sw_sync_ioctl_inc(struct sw_sync_timeline *obj, unsigned long arg) static long sw_sync_ioctl(struct file *file, unsigned
[RFC 22/29] staging/android: remove sync_pt_create()
From: Gustavo Padovanget sw_sync_pt_create() to use fence_create_on_timeline() directly and remove an abstractions layers between fences and its users. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sw_sync.c | 22 ++ drivers/staging/android/sync.c| 20 drivers/staging/android/sync.h| 7 --- 3 files changed, 14 insertions(+), 35 deletions(-) diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index b9f8c51..7250f1b 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -25,16 +25,22 @@ #include "sw_sync.h" +static const struct fence_ops sw_sync_fence_ops = { + .get_driver_name = fence_default_get_driver_name, + .get_timeline_name = fence_default_get_timeline_name, + .enable_signaling = fence_default_enable_signaling, + .signaled = fence_default_signaled, + .wait = fence_default_wait, + .release = fence_default_release, + .fill_driver_data = fence_default_fill_driver_data, + .fence_value_str = fence_default_value_str, + .timeline_value_str = fence_default_timeline_value_str, +}; + struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) { - struct sw_sync_pt *pt; - - pt = (struct sw_sync_pt *) - sync_pt_create(>obj, sizeof(struct sw_sync_pt), value); - - pt->value = value; - - return (struct fence *)pt; + return fence_create_on_timeline(>obj, _sync_fence_ops, +sizeof(struct fence), value); } EXPORT_SYMBOL(sw_sync_pt_create); diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 2365db7..956b4e9 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -31,16 +31,8 @@ #define CREATE_TRACE_POINTS #include "trace/sync.h" -static const struct fence_ops sync_fence_ops; static const struct file_operations sync_fence_fops; -struct fence *sync_pt_create(struct fence_timeline *obj, int size, u32 value) -{ - return fence_create_on_timeline(obj, _fence_ops, - sizeof(struct fence), value); -} -EXPORT_SYMBOL(sync_pt_create); - static struct sync_fence *sync_fence_alloc(int size, const char *name) { struct sync_fence *sync_fence; @@ -305,18 +297,6 @@ int sync_fence_wait(struct sync_fence *sync_fence, long timeout) } EXPORT_SYMBOL(sync_fence_wait); -static const struct fence_ops sync_fence_ops = { - .get_driver_name = fence_default_get_driver_name, - .get_timeline_name = fence_default_get_timeline_name, - .enable_signaling = fence_default_enable_signaling, - .signaled = fence_default_signaled, - .wait = fence_default_wait, - .release = fence_default_release, - .fill_driver_data = fence_default_fill_driver_data, - .fence_value_str = fence_default_value_str, - .timeline_value_str = fence_default_timeline_value_str, -}; - static void sync_fence_free(struct kref *kref) { struct sync_fence *sync_fence = container_of(kref, struct sync_fence, diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index 569873f..256315c 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -78,13 +78,6 @@ static inline void sync_fence_waiter_init(struct sync_fence_waiter *waiter, waiter->callback = callback; } -/* - * API for fence_timeline implementers - */ - -struct fence *sync_pt_create(struct fence_timeline *parent, int size, -u32 value); - /** * sync_fence_create() - creates a sync fence * @name: name of fence to create -- 2.5.0
[RFC 21/29] dma-buf/fence: add fence_create_on_timeline()
From: Gustavo PadovanThis functions in intended to replace sync_pt_create() and it does exactly the same thing sync_pt_create() did. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c| 38 ++ drivers/staging/android/sync.c | 20 ++-- include/linux/fence.h | 3 +++ 3 files changed, 43 insertions(+), 18 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index ec51146..0a07fcb 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -768,6 +768,44 @@ err_free_cb: EXPORT_SYMBOL(fence_wait_any_timeout); /** + * fence_create_on_timeline - create a fence and add it to the timeline + * or until timeout elapses + * @obj: [in]timeline object + * @ops: [in]fence_ops to use + * @size: [in]size to allocate struct fence + * @value: [in]value of this fence + * + * This function allocates a new fence and initialize it as a child of the + * fence_timeline provided. The value received is the seqno used to know + * when the fence is signaled. + * + * Returns NULL if fails to allocate memory or size is too small. + */ +struct fence *fence_create_on_timeline(struct fence_timeline *obj, + const struct fence_ops *ops, int size, + unsigned int value) +{ + unsigned long flags; + struct fence *fence; + + if (size < sizeof(*fence)) + return NULL; + + fence = kzalloc(size, GFP_KERNEL); + if (!fence) + return NULL; + + spin_lock_irqsave(>lock, flags); + fence_timeline_get(obj); + fence_init(fence, ops, >lock, obj->context, value); + list_add_tail(>child_list, >child_list_head); + INIT_LIST_HEAD(>active_list); + spin_unlock_irqrestore(>lock, flags); + return fence; +} +EXPORT_SYMBOL(fence_create_on_timeline); + +/** * fence_init - Initialize a custom fence. * @fence: [in]the fence to initialize * @ops: [in]the fence_ops for operations on this fence diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index a275108..2365db7 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -36,24 +36,8 @@ static const struct file_operations sync_fence_fops; struct fence *sync_pt_create(struct fence_timeline *obj, int size, u32 value) { - unsigned long flags; - struct fence *fence; - - if (size < sizeof(*fence)) - return NULL; - - fence = kzalloc(size, GFP_KERNEL); - if (!fence) - return NULL; - - spin_lock_irqsave(>lock, flags); - fence_timeline_get(obj); - fence_init(fence, _fence_ops, >lock, - obj->context, value); - list_add_tail(>child_list, >child_list_head); - INIT_LIST_HEAD(>active_list); - spin_unlock_irqrestore(>lock, flags); - return fence; + return fence_create_on_timeline(obj, _fence_ops, + sizeof(struct fence), value); } EXPORT_SYMBOL(sync_pt_create); diff --git a/include/linux/fence.h b/include/linux/fence.h index 8908433..adece43 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -212,6 +212,9 @@ struct fence_ops { void (*timeline_value_str)(struct fence *fence, char *str, int size); }; +struct fence *fence_create_on_timeline(struct fence_timeline *obj, + const struct fence_ops *ops, int size, + unsigned int value); void fence_init(struct fence *fence, const struct fence_ops *ops, spinlock_t *lock, unsigned context, unsigned seqno); -- 2.5.0
[RFC 20/29] dma-buf/fence: remove fence_timeline_ops
From: Gustavo Padovanfence_timeline_ops was just workarounding over fence_ops and was used chained in the fence ops. So remove it all to simplify the fence code flow. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 7 ++- drivers/staging/android/sw_sync.c | 20 +--- include/linux/fence.h | 19 ++- 3 files changed, 5 insertions(+), 41 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index d9089a0..ec51146 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -54,7 +54,6 @@ EXPORT_SYMBOL(fence_context_alloc); /** * fence_timeline_create - create a new fence_timeline * @num: [in]amount of contexts to allocate - * @ops: [in]timeline ops of the caller * @size: [in]size to allocate struct fence_timeline * @drv_name: [in]name of the driver * @name: [in]name of the timeline @@ -63,9 +62,8 @@ EXPORT_SYMBOL(fence_context_alloc); * It allocs and initializes a new fence_timeline with a proper fence context * number assigned to it. */ -struct fence_timeline *fence_timeline_create(unsigned num, -struct fence_timeline_ops *ops, -int size, const char *drv_name, +struct fence_timeline *fence_timeline_create(unsigned num, int size, +const char *drv_name, const char *name) { struct fence_timeline *timeline; @@ -78,7 +76,6 @@ struct fence_timeline *fence_timeline_create(unsigned num, return NULL; kref_init(>kref); - timeline->ops = ops; timeline->context = fence_context_alloc(1); strlcpy(timeline->name, name, sizeof(timeline->name)); strlcpy(timeline->drv_name, drv_name, sizeof(timeline->drv_name)); diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index cfd7a18..b9f8c51 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -38,28 +38,10 @@ struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) } EXPORT_SYMBOL(sw_sync_pt_create); -static int sw_sync_fill_driver_data(struct fence *fence, - void *data, int size) -{ - struct sw_sync_pt *pt = (struct sw_sync_pt *)fence; - - if (size < sizeof(pt->value)) - return -ENOMEM; - - memcpy(data, >value, sizeof(pt->value)); - - return sizeof(pt->value); -} - -static struct fence_timeline_ops sw_sync_timeline_ops = { - .fill_driver_data = sw_sync_fill_driver_data, -}; - struct sw_sync_timeline *sw_sync_timeline_create(const char *name) { struct sw_sync_timeline *obj = (struct sw_sync_timeline *) - fence_timeline_create(1, _sync_timeline_ops, -sizeof(struct sw_sync_timeline), + fence_timeline_create(1, sizeof(struct sw_sync_timeline), "sw_sync", name); return obj; diff --git a/include/linux/fence.h b/include/linux/fence.h index 04438c3..8908433 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -30,22 +30,9 @@ #include #include -struct fence_timeline; struct fence; struct fence_ops; struct fence_cb; -/** - * struct fence_timeline_ops - fence context implementation ops - * @fill_driver_data: write implementation specific driver data to data. - * should return an error if there is not enough room - * as specified by size. This information is returned - * to userspace by SYNC_IOC_FENCE_INFO. - * @pt_value_str: fill str with the value of the sync_pt - */ -struct fence_timeline_ops { - /* optional */ - int (*fill_driver_data)(struct fence *fence, void *data, int size); -}; /** * struct fence_timeline - timeline for software synchronization primitive @@ -63,7 +50,6 @@ struct fence_timeline { struct kref kref; charname[32]; chardrv_name[32]; - const struct fence_timeline_ops *ops; booldestroyed; unsigned intvalue; int context; @@ -75,9 +61,8 @@ struct fence_timeline { #endif }; -struct fence_timeline *fence_timeline_create(unsigned num, -struct fence_timeline_ops *ops, -int size, const char *drv_name, +struct fence_timeline *fence_timeline_create(unsigned num, int size, +const char *drv_name, const char *name); void fence_timeline_get(struct fence_timeline *timeline); void fence_timeline_put(struct fence_timeline
[RFC 19/29] dma-buf/fence: create fence_default_fill_driver_data()
From: Gustavo PadovanThe value needed by sw_sync is now inside struct fence so we create a default ops to reply that value for us. --- drivers/dma-buf/fence.c| 21 + drivers/staging/android/sync.c | 12 +--- include/linux/fence.h | 1 + 3 files changed, 23 insertions(+), 11 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 9fdeae8..d9089a0 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -621,6 +621,27 @@ void fence_default_release(struct fence *fence) EXPORT_SYMBOL(fence_default_release); /** + * fence_default_fill_driver_data - fence default .fill_driver_data ops + * @fence: [in]the fence to get the data from + * @data: [out] the data pointer to write the data + * @size: [in]the size of the allocated data + * + * This function return a driver data. In the case the fence seqno value. + * It is used at least by the sw_sync to send fence information to the + * userspace. + */ +int fence_default_fill_driver_data(struct fence *fence, void *data, int size) +{ + if (size < sizeof(fence->seqno)) + return -ENOMEM; + + memcpy(data, >seqno, sizeof(fence->seqno)); + + return sizeof(fence->seqno); +} +EXPORT_SYMBOL(fence_default_fill_driver_data); + +/** * fence_default_value_str - default .fence_value_str fence ops * @fence: [in]the fence to get the value from * @str: [out] the string pointer to write the value diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 147a494..a275108 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -321,16 +321,6 @@ int sync_fence_wait(struct sync_fence *sync_fence, long timeout) } EXPORT_SYMBOL(sync_fence_wait); -static int sync_fence_fill_driver_data(struct fence *fence, - void *data, int size) -{ - struct fence_timeline *parent = fence_parent(fence); - - if (!parent->ops->fill_driver_data) - return 0; - return parent->ops->fill_driver_data(fence, data, size); -} - static const struct fence_ops sync_fence_ops = { .get_driver_name = fence_default_get_driver_name, .get_timeline_name = fence_default_get_timeline_name, @@ -338,7 +328,7 @@ static const struct fence_ops sync_fence_ops = { .signaled = fence_default_signaled, .wait = fence_default_wait, .release = fence_default_release, - .fill_driver_data = sync_fence_fill_driver_data, + .fill_driver_data = fence_default_fill_driver_data, .fence_value_str = fence_default_value_str, .timeline_value_str = fence_default_timeline_value_str, }; diff --git a/include/linux/fence.h b/include/linux/fence.h index 5371beb..04438c3 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -285,6 +285,7 @@ bool fence_default_signaled(struct fence *fence); bool fence_default_enable_signaling(struct fence *fence); signed long fence_default_wait(struct fence *fence, bool intr, signed long timeout); void fence_default_release(struct fence *fence); +int fence_default_fill_driver_data(struct fence *fence, void *data, int size); void fence_default_value_str(struct fence *fence, char *str, int size); void fence_default_timeline_value_str(struct fence *fence, char *str, int size); int fence_add_callback(struct fence *fence, struct fence_cb *cb, -- 2.5.0
[RFC 18/29] dma-buf/fence: create default .fence_value_str() and .timeline_value_str()
From: Gustavo PadovanProvide simple default functions to help users retrieve the values of the fence and the timeline. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 31 +++ drivers/staging/android/sw_sync.c| 18 -- drivers/staging/android/sync.c | 30 ++ drivers/staging/android/sync_debug.c | 11 +-- include/linux/fence.h| 10 ++ include/trace/events/fence.h | 12 +++- 6 files changed, 39 insertions(+), 73 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 786c987..9fdeae8 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -620,6 +620,37 @@ void fence_default_release(struct fence *fence) } EXPORT_SYMBOL(fence_default_release); +/** + * fence_default_value_str - default .fence_value_str fence ops + * @fence: [in]the fence to get the value from + * @str: [out] the string pointer to write the value + * @size: [in]the size of the allocated string + * + * This functions returns a string containing the value of the fence. + */ +void fence_default_value_str(struct fence *fence, char *str, int size) +{ + snprintf(str, size, "%d", fence->seqno); +} +EXPORT_SYMBOL(fence_default_value_str); + +/** + * fence_default_timeline_value_str - default .timeline_value_str fence ops + * @fence: [in]the timeline child fence + * @str: [out] the string pointer to write the value + * @size: [in]the size of the allocated string + * + * This functions returns a string containing the value of the last signaled + * fence in this timeline. + */ +void fence_default_timeline_value_str(struct fence *fence, char *str, int size) +{ + struct fence_timeline *timeline = fence_parent(fence); + + snprintf(str, size, "%d", timeline->value); +} +EXPORT_SYMBOL(fence_default_timeline_value_str); + static bool fence_test_signaled_any(struct fence **fences, uint32_t count) { diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index bed6801..cfd7a18 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -51,26 +51,8 @@ static int sw_sync_fill_driver_data(struct fence *fence, return sizeof(pt->value); } -static void sw_sync_timeline_value_str(struct fence_timeline *fence_timeline, - char *str, int size) -{ - struct sw_sync_timeline *timeline = - (struct sw_sync_timeline *)fence_timeline; - snprintf(str, size, "%d", timeline->value); -} - -static void sw_sync_fence_value_str(struct fence *fence, -char *str, int size) -{ - struct sw_sync_pt *pt = (struct sw_sync_pt *)fence; - - snprintf(str, size, "%d", pt->value); -} - static struct fence_timeline_ops sw_sync_timeline_ops = { .fill_driver_data = sw_sync_fill_driver_data, - .timeline_value_str = sw_sync_timeline_value_str, - .fence_value_str = sw_sync_fence_value_str, }; struct sw_sync_timeline *sw_sync_timeline_create(const char *name) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 8216635..147a494 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -331,32 +331,6 @@ static int sync_fence_fill_driver_data(struct fence *fence, return parent->ops->fill_driver_data(fence, data, size); } -static void sync_fence_value_str(struct fence *fence, - char *str, int size) -{ - struct fence_timeline *parent = fence_parent(fence); - - if (!parent->ops->fence_value_str) { - if (size) - *str = 0; - return; - } - parent->ops->fence_value_str(fence, str, size); -} - -static void sync_fence_timeline_value_str(struct fence *fence, -char *str, int size) -{ - struct fence_timeline *parent = fence_parent(fence); - - if (!parent->ops->timeline_value_str) { - if (size) - *str = 0; - return; - } - parent->ops->timeline_value_str(parent, str, size); -} - static const struct fence_ops sync_fence_ops = { .get_driver_name = fence_default_get_driver_name, .get_timeline_name = fence_default_get_timeline_name, @@ -365,8 +339,8 @@ static const struct fence_ops sync_fence_ops = { .wait = fence_default_wait, .release = fence_default_release, .fill_driver_data = sync_fence_fill_driver_data, - .fence_value_str = sync_fence_value_str, - .timeline_value_str = sync_fence_timeline_value_str, + .fence_value_str = fence_default_value_str, + .timeline_value_str = fence_default_timeline_value_str, }; static void sync_fence_free(struct kref *kref) diff --git
[RFC 17/29] dma-buf/fence: store last signaled value on fence timeline
From: Gustavo PadovanNow fence timeline is aware of the last signaled fence, as it receives the increment to the current value in fence_timeline_signal(). That allow us to create a fence_default_signaled() using timeline->value and fence->seqno in the comparison. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 21 +++-- drivers/staging/android/sw_sync.c | 16 ++-- drivers/staging/android/sync.c| 17 +++-- drivers/staging/android/sync.h| 3 ++- include/linux/fence.h | 12 +++- 5 files changed, 29 insertions(+), 40 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index f77d6a9..786c987 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -149,7 +149,7 @@ void fence_timeline_destroy(struct fence_timeline *timeline) /* * signal any children that their parent is going away. */ - fence_timeline_signal(timeline); + fence_timeline_signal(timeline, 0); fence_timeline_put(timeline); } EXPORT_SYMBOL(fence_timeline_destroy); @@ -157,11 +157,12 @@ EXPORT_SYMBOL(fence_timeline_destroy); /** * fence_timeline_signal - signal fences on a fence_timeline * @timeline [in]the fence_timeline to signal fences + * @inc[in[num to increment on timeline->value * * This function signal fences on a given timeline and remove * those from the active_list. */ -void fence_timeline_signal(struct fence_timeline *timeline) +void fence_timeline_signal(struct fence_timeline *timeline, unsigned int inc) { unsigned long flags; LIST_HEAD(signaled_pts); @@ -169,6 +170,8 @@ void fence_timeline_signal(struct fence_timeline *timeline) spin_lock_irqsave(>lock, flags); + timeline->value += inc; + list_for_each_entry_safe(fence, next, >active_list_head, active_list) { if (fence_is_signaled_locked(fence)) @@ -470,6 +473,20 @@ const char *fence_default_get_timeline_name(struct fence *fence) EXPORT_SYMBOL(fence_default_get_timeline_name); /** + * fence_default_signaled - default .signaled fence ops + * @fence: [in]the fence to check if signaled or not + * + * This functions checks if a fence was signaled or not. + */ +bool fence_default_signaled(struct fence *fence) +{ + struct fence_timeline *timeline = fence_parent(fence); + + return (fence->seqno > timeline->value) ? false : true; +} +EXPORT_SYMBOL(fence_default_signaled); + +/** * fence_default_enable_signaling - default op for .enable_signaling * @fence: [in]the fence to enable signaling * diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index 9720267..bed6801 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -30,7 +30,7 @@ struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) struct sw_sync_pt *pt; pt = (struct sw_sync_pt *) - sync_pt_create(>obj, sizeof(struct sw_sync_pt)); + sync_pt_create(>obj, sizeof(struct sw_sync_pt), value); pt->value = value; @@ -38,15 +38,6 @@ struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) } EXPORT_SYMBOL(sw_sync_pt_create); -static int sw_sync_fence_has_signaled(struct fence *fence) -{ - struct sw_sync_pt *pt = (struct sw_sync_pt *)fence; - struct sw_sync_timeline *obj = - (struct sw_sync_timeline *)fence_parent(fence); - - return (pt->value > obj->value) ? 0 : 1; -} - static int sw_sync_fill_driver_data(struct fence *fence, void *data, int size) { @@ -77,7 +68,6 @@ static void sw_sync_fence_value_str(struct fence *fence, } static struct fence_timeline_ops sw_sync_timeline_ops = { - .has_signaled = sw_sync_fence_has_signaled, .fill_driver_data = sw_sync_fill_driver_data, .timeline_value_str = sw_sync_timeline_value_str, .fence_value_str = sw_sync_fence_value_str, @@ -96,8 +86,6 @@ EXPORT_SYMBOL(sw_sync_timeline_create); void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc) { - obj->value += inc; - - fence_timeline_signal(>obj); + fence_timeline_signal(>obj, inc); } EXPORT_SYMBOL(sw_sync_timeline_inc); diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index f8b3c6b..8216635 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -34,7 +34,7 @@ static const struct fence_ops sync_fence_ops; static const struct file_operations sync_fence_fops; -struct fence *sync_pt_create(struct fence_timeline *obj, int size) +struct fence *sync_pt_create(struct fence_timeline *obj, int size, u32 value) { unsigned long flags; struct fence *fence; @@ -49,7 +49,7 @@ struct fence *sync_pt_create(struct fence_timeline *obj, int
[RFC 16/29] dma-buf/fence: create fence_default_timeline_name()
From: Gustavo PadovanThe fence timeline struct already receives the name of the timeline so we can use a default function to return the timeline name. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c| 14 ++ drivers/staging/android/sync.c | 9 + include/linux/fence.h | 1 + 3 files changed, 16 insertions(+), 8 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 85b5074..f77d6a9 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -456,6 +456,20 @@ const char *fence_default_get_driver_name(struct fence *fence) EXPORT_SYMBOL(fence_default_get_driver_name); /** + * fence_default_get_timeline_name - default get_timeline_name op + * @fence: [in]the fence to retrieve timeline name + * + * This function returns the name of the timeline which the fence belongs to. + */ +const char *fence_default_get_timeline_name(struct fence *fence) +{ + struct fence_timeline *parent = fence_parent(fence); + + return parent->name; +} +EXPORT_SYMBOL(fence_default_get_timeline_name); + +/** * fence_default_enable_signaling - default op for .enable_signaling * @fence: [in]the fence to enable signaling * diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index c3386a6..f8b3c6b 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -321,13 +321,6 @@ int sync_fence_wait(struct sync_fence *sync_fence, long timeout) } EXPORT_SYMBOL(sync_fence_wait); -static const char *sync_fence_get_timeline_name(struct fence *fence) -{ - struct fence_timeline *parent = fence_parent(fence); - - return parent->name; -} - static bool sync_fence_signaled(struct fence *fence) { struct fence_timeline *parent = fence_parent(fence); @@ -377,7 +370,7 @@ static void sync_fence_timeline_value_str(struct fence *fence, static const struct fence_ops sync_fence_ops = { .get_driver_name = fence_default_get_driver_name, - .get_timeline_name = sync_fence_get_timeline_name, + .get_timeline_name = fence_default_get_timeline_name, .enable_signaling = fence_default_enable_signaling, .signaled = sync_fence_signaled, .wait = fence_default_wait, diff --git a/include/linux/fence.h b/include/linux/fence.h index f355c28a..e8f9f12 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -295,6 +295,7 @@ static inline void fence_put(struct fence *fence) int fence_signal(struct fence *fence); int fence_signal_locked(struct fence *fence); const char *fence_default_get_driver_name(struct fence *fence); +const char *fence_default_get_timeline_name(struct fence *fence); bool fence_default_enable_signaling(struct fence *fence); signed long fence_default_wait(struct fence *fence, bool intr, signed long timeout); void fence_default_release(struct fence *fence); -- 2.5.0
[RFC 15/29] dma-buf/fence: create fence_default_get_driver_name()
From: Gustavo PadovanMove driver name handling to fence and create a default function for it. Returns the driver which the fence belongs. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 19 ++- drivers/staging/android/sw_sync.c| 3 +-- drivers/staging/android/sync.c | 9 + drivers/staging/android/sync_debug.c | 2 +- include/linux/fence.h| 8 5 files changed, 25 insertions(+), 16 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index e17397d..85b5074 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -56,6 +56,7 @@ EXPORT_SYMBOL(fence_context_alloc); * @num: [in]amount of contexts to allocate * @ops: [in]timeline ops of the caller * @size: [in]size to allocate struct fence_timeline + * @drv_name: [in]name of the driver * @name: [in]name of the timeline * * This function will return the new fence_timeline or NULL in case of error. @@ -64,7 +65,8 @@ EXPORT_SYMBOL(fence_context_alloc); */ struct fence_timeline *fence_timeline_create(unsigned num, struct fence_timeline_ops *ops, -int size, const char *name) +int size, const char *drv_name, +const char *name) { struct fence_timeline *timeline; @@ -79,6 +81,7 @@ struct fence_timeline *fence_timeline_create(unsigned num, timeline->ops = ops; timeline->context = fence_context_alloc(1); strlcpy(timeline->name, name, sizeof(timeline->name)); + strlcpy(timeline->drv_name, drv_name, sizeof(timeline->drv_name)); INIT_LIST_HEAD(>child_list_head); INIT_LIST_HEAD(>active_list_head); @@ -439,6 +442,20 @@ fence_remove_callback(struct fence *fence, struct fence_cb *cb) EXPORT_SYMBOL(fence_remove_callback); /** + * fence_default_get_driver_name - default .get_driver_name op + * @fence: [in]the fence to get driver name + * + * This function returns the name of the driver that the fence belongs. + */ +const char *fence_default_get_driver_name(struct fence *fence) +{ + struct fence_timeline *parent = fence_parent(fence); + + return parent->drv_name; +} +EXPORT_SYMBOL(fence_default_get_driver_name); + +/** * fence_default_enable_signaling - default op for .enable_signaling * @fence: [in]the fence to enable signaling * diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index 9d6a5bd..9720267 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -77,7 +77,6 @@ static void sw_sync_fence_value_str(struct fence *fence, } static struct fence_timeline_ops sw_sync_timeline_ops = { - .driver_name = "sw_sync", .has_signaled = sw_sync_fence_has_signaled, .fill_driver_data = sw_sync_fill_driver_data, .timeline_value_str = sw_sync_timeline_value_str, @@ -89,7 +88,7 @@ struct sw_sync_timeline *sw_sync_timeline_create(const char *name) struct sw_sync_timeline *obj = (struct sw_sync_timeline *) fence_timeline_create(1, _sync_timeline_ops, sizeof(struct sw_sync_timeline), -name); +"sw_sync", name); return obj; } diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 6cddec9..c3386a6 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -321,13 +321,6 @@ int sync_fence_wait(struct sync_fence *sync_fence, long timeout) } EXPORT_SYMBOL(sync_fence_wait); -static const char *sync_fence_get_driver_name(struct fence *fence) -{ - struct fence_timeline *parent = fence_parent(fence); - - return parent->ops->driver_name; -} - static const char *sync_fence_get_timeline_name(struct fence *fence) { struct fence_timeline *parent = fence_parent(fence); @@ -383,7 +376,7 @@ static void sync_fence_timeline_value_str(struct fence *fence, } static const struct fence_ops sync_fence_ops = { - .get_driver_name = sync_fence_get_driver_name, + .get_driver_name = fence_default_get_driver_name, .get_timeline_name = sync_fence_get_timeline_name, .enable_signaling = fence_default_enable_signaling, .signaled = sync_fence_signaled, diff --git a/drivers/staging/android/sync_debug.c b/drivers/staging/android/sync_debug.c index b8602d2..db618ca 100644 --- a/drivers/staging/android/sync_debug.c +++ b/drivers/staging/android/sync_debug.c @@ -133,7 +133,7 @@ static void sync_print_obj(struct seq_file *s, struct fence_timeline *obj) struct list_head *pos; unsigned long flags; - seq_printf(s, "%s %s", obj->name, obj->ops->driver_name); +
[RFC 14/29] dma-buf/fence: create fence_default_release()
From: Gustavo PadovanAdd a default .release() op to be used on fence_ops vtable. It removes the fences from any list it was added, removes a timeline ref and free the fence. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c| 28 drivers/staging/android/sync.c | 18 +- include/linux/fence.h | 1 + 3 files changed, 30 insertions(+), 17 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 51b77ed..e17397d 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -544,6 +544,34 @@ out: } EXPORT_SYMBOL(fence_default_wait); +/** + * fence_default_release - default .release op + * @fence: [in]the fence to release + * + * This function removes the fence from the child_list * and active_list + * (if it was active) and drops its timeline ref. Finally it frees the + * fence. + */ +void fence_default_release(struct fence *fence) +{ + struct fence_timeline *timeline = fence_parent(fence); + unsigned long flags; + + if (!timeline) + return; + + spin_lock_irqsave(fence->lock, flags); + list_del(>child_list); + if (!list_empty(>active_list)) + list_del(>active_list); + + spin_unlock_irqrestore(fence->lock, flags); + + fence_timeline_put(timeline); + fence_free(fence); +} +EXPORT_SYMBOL(fence_default_release); + static bool fence_test_signaled_any(struct fence **fences, uint32_t count) { diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 87fb93c..6cddec9 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -335,22 +335,6 @@ static const char *sync_fence_get_timeline_name(struct fence *fence) return parent->name; } -static void sync_fence_release(struct fence *fence) -{ - struct fence_timeline *parent = fence_parent(fence); - unsigned long flags; - - spin_lock_irqsave(fence->lock, flags); - list_del(>child_list); - if (!list_empty(>active_list)) - list_del(>active_list); - - spin_unlock_irqrestore(fence->lock, flags); - - fence_timeline_put(parent); - fence_free(fence); -} - static bool sync_fence_signaled(struct fence *fence) { struct fence_timeline *parent = fence_parent(fence); @@ -404,7 +388,7 @@ static const struct fence_ops sync_fence_ops = { .enable_signaling = fence_default_enable_signaling, .signaled = sync_fence_signaled, .wait = fence_default_wait, - .release = sync_fence_release, + .release = fence_default_release, .fill_driver_data = sync_fence_fill_driver_data, .fence_value_str = sync_fence_value_str, .timeline_value_str = sync_fence_timeline_value_str, diff --git a/include/linux/fence.h b/include/linux/fence.h index 73b8c9f..0c97014 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -297,6 +297,7 @@ int fence_signal(struct fence *fence); int fence_signal_locked(struct fence *fence); bool fence_default_enable_signaling(struct fence *fence); signed long fence_default_wait(struct fence *fence, bool intr, signed long timeout); +void fence_default_release(struct fence *fence); int fence_add_callback(struct fence *fence, struct fence_cb *cb, fence_func_t func); bool fence_remove_callback(struct fence *fence, struct fence_cb *cb); -- 2.5.0
[RFC 13/29] dma-buf/fence: create fence_default_enable_signaling()
From: Gustavo PadovanAdd a default .enable_signaling() op to be used on fence_ops vtable. fence_default_enable_signaling() checks if the was not signaled yet and adds it to the active_list. Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c| 22 ++ drivers/staging/android/sync.c | 13 + include/linux/fence.h | 1 + 3 files changed, 24 insertions(+), 12 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 5dcb94c..51b77ed 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -438,6 +438,28 @@ fence_remove_callback(struct fence *fence, struct fence_cb *cb) } EXPORT_SYMBOL(fence_remove_callback); +/** + * fence_default_enable_signaling - default op for .enable_signaling + * @fence: [in]the fence to enable signaling + * + * This function checks if the fence was already signaled and if not + * adds it to the list of active fences. + */ +bool fence_default_enable_signaling(struct fence *fence) +{ + struct fence_timeline *timeline = fence_parent(fence); + + if (!timeline) + return false; + + if (fence->ops->signaled && fence->ops->signaled(fence)) + return false; + + list_add_tail(>active_list, >active_list_head); + return true; +} +EXPORT_SYMBOL(fence_default_enable_signaling); + struct default_wait_cb { struct fence_cb base; struct task_struct *task; diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 417cf9f..87fb93c 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -362,17 +362,6 @@ static bool sync_fence_signaled(struct fence *fence) return ret; } -static bool sync_fence_enable_signaling(struct fence *fence) -{ - struct fence_timeline *parent = fence_parent(fence); - - if (sync_fence_signaled(fence)) - return false; - - list_add_tail(>active_list, >active_list_head); - return true; -} - static int sync_fence_fill_driver_data(struct fence *fence, void *data, int size) { @@ -412,7 +401,7 @@ static void sync_fence_timeline_value_str(struct fence *fence, static const struct fence_ops sync_fence_ops = { .get_driver_name = sync_fence_get_driver_name, .get_timeline_name = sync_fence_get_timeline_name, - .enable_signaling = sync_fence_enable_signaling, + .enable_signaling = fence_default_enable_signaling, .signaled = sync_fence_signaled, .wait = fence_default_wait, .release = sync_fence_release, diff --git a/include/linux/fence.h b/include/linux/fence.h index a333bf37..73b8c9f 100644 --- a/include/linux/fence.h +++ b/include/linux/fence.h @@ -295,6 +295,7 @@ static inline void fence_put(struct fence *fence) int fence_signal(struct fence *fence); int fence_signal_locked(struct fence *fence); +bool fence_default_enable_signaling(struct fence *fence); signed long fence_default_wait(struct fence *fence, bool intr, signed long timeout); int fence_add_callback(struct fence *fence, struct fence_cb *cb, fence_func_t func); -- 2.5.0
[RFC 12/29] staging/android: remove struct sync_pt
From: Gustavo Padovanstruct sync_pt was just wrapping around struct fence and creating an extra abstraction layer. The only two members of struct sync_pt, child_list and active_list, were moved to struct fence in an earlier commit. After removing those two members struct sync_pt is nothing more than struct fence, so remove it all and use struct fence directly. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sw_sync.c| 7 +++--- drivers/staging/android/sw_sync.h| 8 +++ drivers/staging/android/sync.c | 33 - drivers/staging/android/sync.h | 21 -- drivers/staging/android/sync_debug.c | 41 ++-- drivers/staging/android/trace/sync.h | 14 ++-- 6 files changed, 53 insertions(+), 71 deletions(-) diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index 98f9a29..9d6a5bd 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -25,7 +25,7 @@ #include "sw_sync.h" -struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) +struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) { struct sw_sync_pt *pt; @@ -34,7 +34,7 @@ struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) pt->value = value; - return (struct sync_pt *)pt; + return (struct fence *)pt; } EXPORT_SYMBOL(sw_sync_pt_create); @@ -50,8 +50,7 @@ static int sw_sync_fence_has_signaled(struct fence *fence) static int sw_sync_fill_driver_data(struct fence *fence, void *data, int size) { - struct sync_pt *sync_pt = (struct sync_pt *)fence; - struct sw_sync_pt *pt = (struct sw_sync_pt *)sync_pt; + struct sw_sync_pt *pt = (struct sw_sync_pt *)fence; if (size < sizeof(pt->value)) return -ENOMEM; diff --git a/drivers/staging/android/sw_sync.h b/drivers/staging/android/sw_sync.h index cb62298..85ef780 100644 --- a/drivers/staging/android/sw_sync.h +++ b/drivers/staging/android/sw_sync.h @@ -29,7 +29,7 @@ struct sw_sync_timeline { }; struct sw_sync_pt { - struct sync_pt pt; + struct fencept; u32 value; }; @@ -38,7 +38,7 @@ struct sw_sync_pt { struct sw_sync_timeline *sw_sync_timeline_create(const char *name); void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc); -struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value); +struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value); #else static inline struct sw_sync_timeline *sw_sync_timeline_create(const char *name) { @@ -49,8 +49,8 @@ static inline void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc) { } -static inline struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, - u32 value) +static inline struct fence *sw_sync_pt_create(struct sw_sync_timeline *obj, + u32 value) { return NULL; } diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index b07bc24..417cf9f 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -39,7 +39,7 @@ struct fence *sync_pt_create(struct fence_timeline *obj, int size) unsigned long flags; struct fence *fence; - if (size < sizeof(struct sync_pt)) + if (size < sizeof(*fence)) return NULL; fence = kzalloc(size, GFP_KERNEL); @@ -57,12 +57,6 @@ struct fence *sync_pt_create(struct fence_timeline *obj, int size) } EXPORT_SYMBOL(sync_pt_create); -void sync_pt_free(struct sync_pt *pt) -{ - fence_put(>base); -} -EXPORT_SYMBOL(sync_pt_free); - static struct sync_fence *sync_fence_alloc(int size, const char *name) { struct sync_fence *sync_fence; @@ -101,7 +95,7 @@ static void fence_check_cb_func(struct fence *f, struct fence_cb *cb) } /* TODO: implement a create which takes more that one sync_pt */ -struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt) +struct sync_fence *sync_fence_create_dma(const char *name, struct fence *fence) { struct sync_fence *sync_fence; @@ -113,9 +107,10 @@ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt) sync_fence->num_fences = 1; atomic_set(_fence->status, 1); - sync_fence->cbs[0].fence = pt; + sync_fence->cbs[0].fence = fence; sync_fence->cbs[0].sync_fence = sync_fence; - if (fence_add_callback(pt, _fence->cbs[0].cb, fence_check_cb_func)) + if (fence_add_callback(fence, _fence->cbs[0].cb, + fence_check_cb_func)) atomic_dec(_fence->status); sync_fence_debug_add(sync_fence); @@ -124,9 +119,9 @@ struct sync_fence *sync_fence_create_dma(const
[RFC 11/29] dma-buf/fence: move sync_timeline to fence_timeline
From: Gustavo PadovanAdd the sync timeline from sync framework to fence synchronization system. This is an attempt to remove some duplication between sync.c and fence.c The sync_timeline was no more than a wrapper on top of the fence framework to be used by sw_sync. It simplifies some accesses, for example, when you have a struct fence you don't need get the sync_pt related to it to know the parent timeline, it is just a matter of calling fence_parent() now. This is just the initial step, the idea is to connect sw_sync direct with fences removing some abstractions in between. The sync API changes here are: * struct sync_timeline is now struct fence_timeline * sync_timeline_ops is now fence_timeline_ops and they now carry struct fence as parameter instead of struct sync_pt * sync_timeline_create() -> fence_timeline_create() * sync_timeline_get() -> fence_timeline_get() * sync_timeline_put() -> fence_timeline_put() * sync_timeline_destroy() -> fence_timeline_destroy() * sync_timeline_signal() -> fence_timeline_signal() Signed-off-by: Gustavo Padovan --- drivers/dma-buf/fence.c | 125 + drivers/staging/android/sw_sync.c| 27 --- drivers/staging/android/sw_sync.h| 2 +- drivers/staging/android/sync.c | 150 +++ drivers/staging/android/sync.h | 130 +- drivers/staging/android/sync_debug.c | 26 +++--- drivers/staging/android/trace/sync.h | 24 -- include/linux/fence.h| 75 ++ include/trace/events/fence.h | 24 ++ 9 files changed, 285 insertions(+), 298 deletions(-) diff --git a/drivers/dma-buf/fence.c b/drivers/dma-buf/fence.c index 7b05dbe..5dcb94c 100644 --- a/drivers/dma-buf/fence.c +++ b/drivers/dma-buf/fence.c @@ -52,6 +52,131 @@ unsigned fence_context_alloc(unsigned num) EXPORT_SYMBOL(fence_context_alloc); /** + * fence_timeline_create - create a new fence_timeline + * @num: [in]amount of contexts to allocate + * @ops: [in]timeline ops of the caller + * @size: [in]size to allocate struct fence_timeline + * @name: [in]name of the timeline + * + * This function will return the new fence_timeline or NULL in case of error. + * It allocs and initializes a new fence_timeline with a proper fence context + * number assigned to it. + */ +struct fence_timeline *fence_timeline_create(unsigned num, +struct fence_timeline_ops *ops, +int size, const char *name) +{ + struct fence_timeline *timeline; + + if (size < sizeof(*timeline)) + return NULL; + + timeline = kzalloc(size, GFP_KERNEL); + if (!timeline) + return NULL; + + kref_init(>kref); + timeline->ops = ops; + timeline->context = fence_context_alloc(1); + strlcpy(timeline->name, name, sizeof(timeline->name)); + + INIT_LIST_HEAD(>child_list_head); + INIT_LIST_HEAD(>active_list_head); + spin_lock_init(>lock); + + return timeline; +} +EXPORT_SYMBOL(fence_timeline_create); + +/** + * fence_timeline_free - free resources of fence_timeline + * @kref [in]the kref of the fence_timeline to be freed + * + * This function frees a fence_timeline which is matter of a simple + * call to kfree() + */ +static void fence_timeline_free(struct kref *kref) +{ + struct fence_timeline *timeline = + container_of(kref, struct fence_timeline, kref); + + kfree(timeline); +} + +/** + * fence_timeline_get - get a reference to the timeline + * @timeline [in]the fence_timeline to get a reference + * + * This function increase the refcnt for the given timeline. + */ +void fence_timeline_get(struct fence_timeline *timeline) +{ + kref_get(>kref); +} +EXPORT_SYMBOL(fence_timeline_get); + +/** + * fence_timeline_put - put a reference to the timeline + * @timeline [in]the fence_timeline to put a reference + * + * This function decreases the refcnt for the given timeline + * and frees it if gets to zero. + */ +void fence_timeline_put(struct fence_timeline *timeline) +{ + kref_put(>kref, fence_timeline_free); +} +EXPORT_SYMBOL(fence_timeline_put); + +/** + * fence_timeline_destroy - destroy a fence_timeline + * @timeline [in]the fence_timeline to destroy + * + * This function destroys a timeline. It signals any active fence first. + */ +void fence_timeline_destroy(struct fence_timeline *timeline) +{ + timeline->destroyed = true; + /* +* Ensure timeline is marked as destroyed before +* changing timeline's fences status. +*/ + smp_wmb(); + + /* +* signal any children that their parent is going away. +*/ + fence_timeline_signal(timeline); + fence_timeline_put(timeline); +}
[RFC 10/29] staging/android: rename 'sync_pt' to 'fence' in struct sync_fence_cb
From: Gustavo Padovan'sync_pt' is actually declared as struct fence so to make the name means its type we rename it to 'fence'. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.c | 20 ++-- drivers/staging/android/sync.h | 2 +- drivers/staging/android/sync_debug.c | 2 +- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index c47b68d..decff9e 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -197,7 +197,7 @@ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt) sync_fence->num_fences = 1; atomic_set(_fence->status, 1); - sync_fence->cbs[0].sync_pt = pt; + sync_fence->cbs[0].fence = pt; sync_fence->cbs[0].sync_fence = sync_fence; if (fence_add_callback(pt, _fence->cbs[0].cb, fence_check_cb_func)) atomic_dec(_fence->status); @@ -247,7 +247,7 @@ EXPORT_SYMBOL(sync_fence_install); static void sync_fence_add_pt(struct sync_fence *sync_fence, int *i, struct fence *pt) { - sync_fence->cbs[*i].sync_pt = pt; + sync_fence->cbs[*i].fence = pt; sync_fence->cbs[*i].sync_fence = sync_fence; if (!fence_add_callback(pt, _fence->cbs[*i].cb, @@ -279,8 +279,8 @@ struct sync_fence *sync_fence_merge(const char *name, * and sync_fence_create, this is a reasonable assumption. */ for (i = i_a = i_b = 0; i_a < a->num_fences && i_b < b->num_fences; ) { - struct fence *pt_a = a->cbs[i_a].sync_pt; - struct fence *pt_b = b->cbs[i_b].sync_pt; + struct fence *pt_a = a->cbs[i_a].fence; + struct fence *pt_b = b->cbs[i_b].fence; if (pt_a->context < pt_b->context) { sync_fence_add_pt(sync_fence, , pt_a); @@ -302,10 +302,10 @@ struct sync_fence *sync_fence_merge(const char *name, } for (; i_a < a->num_fences; i_a++) - sync_fence_add_pt(sync_fence, , a->cbs[i_a].sync_pt); + sync_fence_add_pt(sync_fence, , a->cbs[i_a].fence); for (; i_b < b->num_fences; i_b++) - sync_fence_add_pt(sync_fence, , b->cbs[i_b].sync_pt); + sync_fence_add_pt(sync_fence, , b->cbs[i_b].fence); if (num_fences > i) atomic_sub(num_fences - i, _fence->status); @@ -384,7 +384,7 @@ int sync_fence_wait(struct sync_fence *sync_fence, long timeout) trace_sync_wait(sync_fence, 1); for (i = 0; i < sync_fence->num_fences; ++i) - trace_sync_pt(sync_fence->cbs[i].sync_pt); + trace_sync_pt(sync_fence->cbs[i].fence); ret = wait_event_interruptible_timeout(sync_fence->wq, atomic_read(_fence->status) <= 0, timeout); @@ -525,9 +525,9 @@ static void sync_fence_free(struct kref *kref) int i; for (i = 0; i < sync_fence->num_fences; ++i) { - fence_remove_callback(sync_fence->cbs[i].sync_pt, + fence_remove_callback(sync_fence->cbs[i].fence, _fence->cbs[i].cb); - fence_put(sync_fence->cbs[i].sync_pt); + fence_put(sync_fence->cbs[i].fence); } kfree(sync_fence); @@ -681,7 +681,7 @@ static long sync_fence_ioctl_fence_info(struct sync_fence *sync_fence, len = sizeof(struct sync_fence_info_data); for (i = 0; i < sync_fence->num_fences; ++i) { - struct fence *pt = sync_fence->cbs[i].sync_pt; + struct fence *pt = sync_fence->cbs[i].fence; ret = sync_fill_pt_info(pt, (u8 *)data + len, size - len); diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index 0fed642..43f72a7 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -110,7 +110,7 @@ static inline struct sync_timeline *sync_pt_parent(struct sync_pt *pt) struct sync_fence_cb { struct fence_cb cb; - struct fence *sync_pt; + struct fence *fence; struct sync_fence *sync_fence; }; diff --git a/drivers/staging/android/sync_debug.c b/drivers/staging/android/sync_debug.c index cfa92d2..78e9147 100644 --- a/drivers/staging/android/sync_debug.c +++ b/drivers/staging/android/sync_debug.c @@ -163,7 +163,7 @@ static void sync_print_sync_fence(struct seq_file *s, sync_status_str(atomic_read(_fence->status))); for (i = 0; i < sync_fence->num_fences; ++i) { - sync_print_pt(s, sync_fence->cbs[i].sync_pt, true); + sync_print_pt(s, sync_fence->cbs[i].fence, true); } spin_lock_irqsave(_fence->wq.lock, flags); -- 2.5.0
[RFC 09/29] staging/android: rename struct sync_fence's variables to 'sync_fence'
From: Gustavo PadovanTo avoid confusion with struct fence vars that are most of the time called 'fence' as well we should rename all struct sync_fence's to sync_fence. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.c | 192 ++- drivers/staging/android/sync.h | 2 +- drivers/staging/android/sync_debug.c | 39 +++ 3 files changed, 120 insertions(+), 113 deletions(-) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 273aa4b..c47b68d 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -149,61 +149,62 @@ EXPORT_SYMBOL(sync_pt_free); static struct sync_fence *sync_fence_alloc(int size, const char *name) { - struct sync_fence *fence; + struct sync_fence *sync_fence; - fence = kzalloc(size, GFP_KERNEL); - if (!fence) + sync_fence = kzalloc(size, GFP_KERNEL); + if (!sync_fence) return NULL; - fence->file = anon_inode_getfile("sync_fence", _fence_fops, -fence, 0); - if (IS_ERR(fence->file)) + sync_fence->file = anon_inode_getfile("sync_fence", _fence_fops, + sync_fence, 0); + if (IS_ERR(sync_fence->file)) goto err; - kref_init(>kref); - strlcpy(fence->name, name, sizeof(fence->name)); + kref_init(_fence->kref); + strlcpy(sync_fence->name, name, sizeof(sync_fence->name)); - init_waitqueue_head(>wq); + init_waitqueue_head(_fence->wq); - return fence; + return sync_fence; err: - kfree(fence); + kfree(sync_fence); return NULL; } static void fence_check_cb_func(struct fence *f, struct fence_cb *cb) { struct sync_fence_cb *check; - struct sync_fence *fence; + struct sync_fence *sync_fence; check = container_of(cb, struct sync_fence_cb, cb); - fence = check->fence; + sync_fence = check->sync_fence; - if (atomic_dec_and_test(>status)) - wake_up_all(>wq); + if (atomic_dec_and_test(_fence->status)) + wake_up_all(_fence->wq); } /* TODO: implement a create which takes more that one sync_pt */ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt) { - struct sync_fence *fence; + struct sync_fence *sync_fence; - fence = sync_fence_alloc(offsetof(struct sync_fence, cbs[1]), name); - if (!fence) + sync_fence = sync_fence_alloc(offsetof(struct sync_fence, cbs[1]), + name); + if (!sync_fence) return NULL; - fence->num_fences = 1; - atomic_set(>status, 1); + sync_fence->num_fences = 1; + atomic_set(_fence->status, 1); - fence->cbs[0].sync_pt = pt; - fence->cbs[0].fence = fence; - if (fence_add_callback(pt, >cbs[0].cb, fence_check_cb_func)) - atomic_dec(>status); + sync_fence->cbs[0].sync_pt = pt; + sync_fence->cbs[0].sync_fence = sync_fence; + if (fence_add_callback(pt, _fence->cbs[0].cb, fence_check_cb_func)) + atomic_dec(_fence->status); - sync_fence_debug_add(fence); + sync_fence_debug_add(sync_fence); - return fence; + return sync_fence; } EXPORT_SYMBOL(sync_fence_create_dma); @@ -231,25 +232,26 @@ err: } EXPORT_SYMBOL(sync_fence_fdget); -void sync_fence_put(struct sync_fence *fence) +void sync_fence_put(struct sync_fence *sync_fence) { - fput(fence->file); + fput(sync_fence->file); } EXPORT_SYMBOL(sync_fence_put); -void sync_fence_install(struct sync_fence *fence, int fd) +void sync_fence_install(struct sync_fence *sync_fence, int fd) { - fd_install(fd, fence->file); + fd_install(fd, sync_fence->file); } EXPORT_SYMBOL(sync_fence_install); -static void sync_fence_add_pt(struct sync_fence *fence, +static void sync_fence_add_pt(struct sync_fence *sync_fence, int *i, struct fence *pt) { - fence->cbs[*i].sync_pt = pt; - fence->cbs[*i].fence = fence; + sync_fence->cbs[*i].sync_pt = pt; + sync_fence->cbs[*i].sync_fence = sync_fence; - if (!fence_add_callback(pt, >cbs[*i].cb, fence_check_cb_func)) { + if (!fence_add_callback(pt, _fence->cbs[*i].cb, + fence_check_cb_func)) { fence_get(pt); (*i)++; } @@ -259,15 +261,15 @@ struct sync_fence *sync_fence_merge(const char *name, struct sync_fence *a, struct sync_fence *b) { int num_fences = a->num_fences + b->num_fences; - struct sync_fence *fence; + struct sync_fence *sync_fence; int i, i_a, i_b; unsigned long size = offsetof(struct sync_fence, cbs[num_fences]); - fence = sync_fence_alloc(size, name); -
[RFC 08/29] staging/android: Remove WARN_ON_ONCE when releasing sync_fence
From: Gustavo PadovanThere isn't any problem on removing the sync_pts from the active_list when the fence is released. If the user decides to close the fence before it is signaled we should do it and not warn about anything. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 5028847..273aa4b 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -432,8 +432,9 @@ static void sync_fence_release(struct fence *fence) spin_lock_irqsave(fence->lock, flags); list_del(>child_list); - if (WARN_ON_ONCE(!list_empty(>active_list))) + if (!list_empty(>active_list)) list_del(>active_list); + spin_unlock_irqrestore(fence->lock, flags); sync_timeline_put(parent); -- 2.5.0
[RFC 07/29] staging/android: move sw_sync file to debugfs file
From: Gustavo PadovanThis remove CONFIG_SW_SYNC_USER and instead compile the sw_sync file into debugpfs under /sync/sw_sync. Signed-off-by: Gustavo Padovan --- drivers/staging/android/Kconfig | 9 --- drivers/staging/android/sw_sync.c| 129 --- drivers/staging/android/sync_debug.c | 118 +++- 3 files changed, 117 insertions(+), 139 deletions(-) diff --git a/drivers/staging/android/Kconfig b/drivers/staging/android/Kconfig index 42b1512..bd90d20 100644 --- a/drivers/staging/android/Kconfig +++ b/drivers/staging/android/Kconfig @@ -57,15 +57,6 @@ config SW_SYNC synchronization. Useful when there is no hardware primitive backing the synchronization. -config SW_SYNC_USER - bool "Userspace API for SW_SYNC" - default n - depends on SW_SYNC - ---help--- - Provides a user space API to the sw sync object. - *WARNING* improper use of this can result in deadlocking kernel - drivers from userspace. - source "drivers/staging/android/ion/Kconfig" endif # if ANDROID diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index 566dcdc..f491dbc 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -102,132 +102,3 @@ void sw_sync_timeline_inc(struct sw_sync_timeline *obj, u32 inc) sync_timeline_signal(>obj); } EXPORT_SYMBOL(sw_sync_timeline_inc); - -#ifdef CONFIG_SW_SYNC_USER -/* *WARNING* - * - * improper use of this can result in deadlocking kernel drivers from userspace. - */ - -/* opening sw_sync create a new sync obj */ -static int sw_sync_open(struct inode *inode, struct file *file) -{ - struct sw_sync_timeline *obj; - char task_comm[TASK_COMM_LEN]; - - get_task_comm(task_comm, current); - - obj = sw_sync_timeline_create(task_comm); - if (!obj) - return -ENOMEM; - - file->private_data = obj; - - return 0; -} - -static int sw_sync_release(struct inode *inode, struct file *file) -{ - struct sw_sync_timeline *obj = file->private_data; - - sync_timeline_destroy(>obj); - return 0; -} - -static long sw_sync_ioctl_create_fence(struct sw_sync_timeline *obj, - unsigned long arg) -{ - int fd = get_unused_fd_flags(O_CLOEXEC); - int err; - struct sync_pt *pt; - struct sync_fence *fence; - struct sw_sync_create_fence_data data; - - if (fd < 0) - return fd; - - if (copy_from_user(, (void __user *)arg, sizeof(data))) { - err = -EFAULT; - goto err; - } - - pt = sw_sync_pt_create(obj, data.value); - if (!pt) { - err = -ENOMEM; - goto err; - } - - data.name[sizeof(data.name) - 1] = '\0'; - fence = sync_fence_create(data.name, pt); - if (!fence) { - sync_pt_free(pt); - err = -ENOMEM; - goto err; - } - - data.fence = fd; - if (copy_to_user((void __user *)arg, , sizeof(data))) { - sync_fence_put(fence); - err = -EFAULT; - goto err; - } - - sync_fence_install(fence, fd); - - return 0; - -err: - put_unused_fd(fd); - return err; -} - -static long sw_sync_ioctl_inc(struct sw_sync_timeline *obj, unsigned long arg) -{ - u32 value; - - if (copy_from_user(, (void __user *)arg, sizeof(value))) - return -EFAULT; - - sw_sync_timeline_inc(obj, value); - - return 0; -} - -static long sw_sync_ioctl(struct file *file, unsigned int cmd, - unsigned long arg) -{ - struct sw_sync_timeline *obj = file->private_data; - - switch (cmd) { - case SW_SYNC_IOC_CREATE_FENCE: - return sw_sync_ioctl_create_fence(obj, arg); - - case SW_SYNC_IOC_INC: - return sw_sync_ioctl_inc(obj, arg); - - default: - return -ENOTTY; - } -} - -static const struct file_operations sw_sync_fops = { - .owner = THIS_MODULE, - .open = sw_sync_open, - .release = sw_sync_release, - .unlocked_ioctl = sw_sync_ioctl, - .compat_ioctl = sw_sync_ioctl, -}; - -static struct miscdevice sw_sync_dev = { - .minor = MISC_DYNAMIC_MINOR, - .name = "sw_sync", - .fops = _sync_fops, -}; - -static int __init sw_sync_device_init(void) -{ - return misc_register(_sync_dev); -} -device_initcall(sw_sync_device_init); - -#endif /* CONFIG_SW_SYNC_USER */ diff --git a/drivers/staging/android/sync_debug.c b/drivers/staging/android/sync_debug.c index 86d683b..0a2df3f 100644 --- a/drivers/staging/android/sync_debug.c +++ b/drivers/staging/android/sync_debug.c @@ -27,7 +27,7 @@ #include #include #include -#include "sync.h" +#include "sw_sync.h" #ifdef CONFIG_DEBUG_FS @@
[RFC 06/29] staging/android: create a 'sync' dir for debugfs information
From: Gustavo PadovanCreates the 'sync' dir on debugfs root dir and move the 'sync' file to sync/info. This is the preparation to add more debug info and control. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync_debug.c | 21 + 1 file changed, 17 insertions(+), 4 deletions(-) diff --git a/drivers/staging/android/sync_debug.c b/drivers/staging/android/sync_debug.c index f45d13c..86d683b 100644 --- a/drivers/staging/android/sync_debug.c +++ b/drivers/staging/android/sync_debug.c @@ -15,6 +15,7 @@ */ #include +#include #include #include #include @@ -30,6 +31,8 @@ #ifdef CONFIG_DEBUG_FS +static struct dentry *dbgfs; + static LIST_HEAD(sync_timeline_list_head); static DEFINE_SPINLOCK(sync_timeline_list_lock); static LIST_HEAD(sync_fence_list_head); @@ -208,13 +211,13 @@ static int sync_debugfs_show(struct seq_file *s, void *unused) return 0; } -static int sync_debugfs_open(struct inode *inode, struct file *file) +static int sync_info_debugfs_open(struct inode *inode, struct file *file) { return single_open(file, sync_debugfs_show, inode->i_private); } -static const struct file_operations sync_debugfs_fops = { - .open = sync_debugfs_open, +static const struct file_operations sync_info_debugfs_fops = { + .open = sync_info_debugfs_open, .read = seq_read, .llseek = seq_lseek, .release= single_release, @@ -222,11 +225,21 @@ static const struct file_operations sync_debugfs_fops = { static __init int sync_debugfs_init(void) { - debugfs_create_file("sync", S_IRUGO, NULL, NULL, _debugfs_fops); + dbgfs = debugfs_create_dir("sync", NULL); + + debugfs_create_file("info", 0444, dbgfs, NULL, _info_debugfs_fops); + return 0; } late_initcall(sync_debugfs_init); +static __exit void sync_debugfs_exit(void) +{ + if (dbgfs) + debugfs_remove_recursive(dbgfs); +} +module_exit(sync_debugfs_exit); + #define DUMP_CHUNK 256 static char sync_dump_buf[64 * 1024]; void sync_dump(void) -- 2.5.0
[RFC 05/29] staging/android: remove not used sync_timeline ops
From: Gustavo Padovan.dup and .compare are not used by the sync framework, so remove them from sw_sync. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sw_sync.c | 29 + drivers/staging/android/sync.c| 6 -- drivers/staging/android/sync.h| 19 --- 3 files changed, 1 insertion(+), 53 deletions(-) diff --git a/drivers/staging/android/sw_sync.c b/drivers/staging/android/sw_sync.c index c4ff167..566dcdc 100644 --- a/drivers/staging/android/sw_sync.c +++ b/drivers/staging/android/sw_sync.c @@ -25,14 +25,6 @@ #include "sw_sync.h" -static int sw_sync_cmp(u32 a, u32 b) -{ - if (a == b) - return 0; - - return ((s32)a - (s32)b) < 0 ? -1 : 1; -} - struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) { struct sw_sync_pt *pt; @@ -46,30 +38,13 @@ struct sync_pt *sw_sync_pt_create(struct sw_sync_timeline *obj, u32 value) } EXPORT_SYMBOL(sw_sync_pt_create); -static struct sync_pt *sw_sync_pt_dup(struct sync_pt *sync_pt) -{ - struct sw_sync_pt *pt = (struct sw_sync_pt *)sync_pt; - struct sw_sync_timeline *obj = - (struct sw_sync_timeline *)sync_pt_parent(sync_pt); - - return (struct sync_pt *)sw_sync_pt_create(obj, pt->value); -} - static int sw_sync_pt_has_signaled(struct sync_pt *sync_pt) { struct sw_sync_pt *pt = (struct sw_sync_pt *)sync_pt; struct sw_sync_timeline *obj = (struct sw_sync_timeline *)sync_pt_parent(sync_pt); - return sw_sync_cmp(obj->value, pt->value) >= 0; -} - -static int sw_sync_pt_compare(struct sync_pt *a, struct sync_pt *b) -{ - struct sw_sync_pt *pt_a = (struct sw_sync_pt *)a; - struct sw_sync_pt *pt_b = (struct sw_sync_pt *)b; - - return sw_sync_cmp(pt_a->value, pt_b->value); + return (pt->value > obj->value) ? 0 : 1; } static int sw_sync_fill_driver_data(struct sync_pt *sync_pt, @@ -103,9 +78,7 @@ static void sw_sync_pt_value_str(struct sync_pt *sync_pt, static struct sync_timeline_ops sw_sync_timeline_ops = { .driver_name = "sw_sync", - .dup = sw_sync_pt_dup, .has_signaled = sw_sync_pt_has_signaled, - .compare = sw_sync_pt_compare, .fill_driver_data = sw_sync_fill_driver_data, .timeline_value_str = sw_sync_timeline_value_str, .pt_value_str = sw_sync_pt_value_str, diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index fa756ef..5028847 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -68,9 +68,6 @@ static void sync_timeline_free(struct kref *kref) sync_timeline_debug_remove(obj); - if (obj->ops->release_obj) - obj->ops->release_obj(obj); - kfree(obj); } @@ -439,9 +436,6 @@ static void sync_fence_release(struct fence *fence) list_del(>active_list); spin_unlock_irqrestore(fence->lock, flags); - if (parent->ops->free_pt) - parent->ops->free_pt(pt); - sync_timeline_put(parent); fence_free(>base); } diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index f3d4f75..ad45659 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -30,17 +30,10 @@ struct sync_fence; /** * struct sync_timeline_ops - sync object implementation ops * @driver_name: name of the implementation - * @dup: duplicate a sync_pt * @has_signaled: returns: * 1 if pt has signaled * 0 if pt has not signaled * <0 on error - * @compare: returns: - * 1 if b will signal before a - * 0 if a and b will signal at the same time - * -1 if a will signal before b - * @free_pt: called before sync_pt is freed - * @release_obj: called before sync_timeline is freed * @fill_driver_data: write implementation specific driver data to data. * should return an error if there is not enough room * as specified by size. This information is returned @@ -52,20 +45,8 @@ struct sync_timeline_ops { const char *driver_name; /* required */ - struct sync_pt * (*dup)(struct sync_pt *pt); - - /* required */ int (*has_signaled)(struct sync_pt *pt); - /* required */ - int (*compare)(struct sync_pt *a, struct sync_pt *b); - - /* optional */ - void (*free_pt)(struct sync_pt *sync_pt); - - /* optional */ - void (*release_obj)(struct sync_timeline *sync_timeline); - /* optional */ int (*fill_driver_data)(struct sync_pt *syncpt, void *data, int size); -- 2.5.0
[RFC 04/29] staging/android: rename 'android_fence' to 'sync_fence'
From: Gustavo PadovanAs we are de-staging it rename it to a name that is not related to android. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.c | 40 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index 4926bb0..fa756ef 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -31,7 +31,7 @@ #define CREATE_TRACE_POINTS #include "trace/sync.h" -static const struct fence_ops android_fence_ops; +static const struct fence_ops sync_fence_ops; static const struct file_operations sync_fence_fops; struct sync_timeline *sync_timeline_create(const struct sync_timeline_ops *ops, @@ -135,7 +135,7 @@ struct sync_pt *sync_pt_create(struct sync_timeline *obj, int size) spin_lock_irqsave(>child_list_lock, flags); sync_timeline_get(obj); - fence_init(>base, _fence_ops, >child_list_lock, + fence_init(>base, _fence_ops, >child_list_lock, obj->context, ++obj->value); list_add_tail(>child_list, >child_list_head); INIT_LIST_HEAD(>active_list); @@ -411,7 +411,7 @@ int sync_fence_wait(struct sync_fence *fence, long timeout) } EXPORT_SYMBOL(sync_fence_wait); -static const char *android_fence_get_driver_name(struct fence *fence) +static const char *sync_fence_get_driver_name(struct fence *fence) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); struct sync_timeline *parent = sync_pt_parent(pt); @@ -419,7 +419,7 @@ static const char *android_fence_get_driver_name(struct fence *fence) return parent->ops->driver_name; } -static const char *android_fence_get_timeline_name(struct fence *fence) +static const char *sync_fence_get_timeline_name(struct fence *fence) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); struct sync_timeline *parent = sync_pt_parent(pt); @@ -427,7 +427,7 @@ static const char *android_fence_get_timeline_name(struct fence *fence) return parent->name; } -static void android_fence_release(struct fence *fence) +static void sync_fence_release(struct fence *fence) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); struct sync_timeline *parent = sync_pt_parent(pt); @@ -446,7 +446,7 @@ static void android_fence_release(struct fence *fence) fence_free(>base); } -static bool android_fence_signaled(struct fence *fence) +static bool sync_fence_signaled(struct fence *fence) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); struct sync_timeline *parent = sync_pt_parent(pt); @@ -458,19 +458,19 @@ static bool android_fence_signaled(struct fence *fence) return ret; } -static bool android_fence_enable_signaling(struct fence *fence) +static bool sync_fence_enable_signaling(struct fence *fence) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); struct sync_timeline *parent = sync_pt_parent(pt); - if (android_fence_signaled(fence)) + if (sync_fence_signaled(fence)) return false; list_add_tail(>active_list, >active_list_head); return true; } -static int android_fence_fill_driver_data(struct fence *fence, +static int sync_fence_fill_driver_data(struct fence *fence, void *data, int size) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); @@ -481,7 +481,7 @@ static int android_fence_fill_driver_data(struct fence *fence, return parent->ops->fill_driver_data(pt, data, size); } -static void android_fence_value_str(struct fence *fence, +static void sync_fence_value_str(struct fence *fence, char *str, int size) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); @@ -495,7 +495,7 @@ static void android_fence_value_str(struct fence *fence, parent->ops->pt_value_str(pt, str, size); } -static void android_fence_timeline_value_str(struct fence *fence, +static void sync_fence_timeline_value_str(struct fence *fence, char *str, int size) { struct sync_pt *pt = container_of(fence, struct sync_pt, base); @@ -509,16 +509,16 @@ static void android_fence_timeline_value_str(struct fence *fence, parent->ops->timeline_value_str(parent, str, size); } -static const struct fence_ops android_fence_ops = { - .get_driver_name = android_fence_get_driver_name, - .get_timeline_name = android_fence_get_timeline_name, - .enable_signaling = android_fence_enable_signaling, - .signaled = android_fence_signaled, +static const struct fence_ops sync_fence_ops = { + .get_driver_name = sync_fence_get_driver_name, + .get_timeline_name = sync_fence_get_timeline_name, + .enable_signaling =
[RFC 03/29] staging/android: rename sync_fence_release
From: Gustavo PadovanTo avoid collision with an upcoming rename change the name of sync_fence_release() to sync_fence_release_file() Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/staging/android/sync.c b/drivers/staging/android/sync.c index ed43796..4926bb0 100644 --- a/drivers/staging/android/sync.c +++ b/drivers/staging/android/sync.c @@ -534,7 +534,7 @@ static void sync_fence_free(struct kref *kref) kfree(fence); } -static int sync_fence_release(struct inode *inode, struct file *file) +static int sync_fence_file_release(struct inode *inode, struct file *file) { struct sync_fence *fence = file->private_data; @@ -724,7 +724,7 @@ static long sync_fence_ioctl(struct file *file, unsigned int cmd, } static const struct file_operations sync_fence_fops = { - .release = sync_fence_release, + .release = sync_fence_file_release, .poll = sync_fence_poll, .unlocked_ioctl = sync_fence_ioctl, .compat_ioctl = sync_fence_ioctl, -- 2.5.0
[RFC 02/29] staging/android: fix checkpatch warning
From: Gustavo PadovanTrivial indentation fix. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index 7a4d820..f3d4f75 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -358,6 +358,6 @@ void sync_dump(void); # define sync_dump() #endif int sync_fence_wake_up_wq(wait_queue_t *curr, unsigned mode, -int wake_flags, void *key); + int wake_flags, void *key); #endif /* _LINUX_SYNC_H */ -- 2.5.0
[RFC 01/29] staging/android: fix sync framework documentation
From: Gustavo PadovanUpdates comments about functions and structures. Signed-off-by: Gustavo Padovan --- drivers/staging/android/sync.h | 45 -- 1 file changed, 21 insertions(+), 24 deletions(-) diff --git a/drivers/staging/android/sync.h b/drivers/staging/android/sync.h index afa0752..7a4d820 100644 --- a/drivers/staging/android/sync.h +++ b/drivers/staging/android/sync.h @@ -110,15 +110,9 @@ struct sync_timeline { /** * struct sync_pt - sync point - * @fence: base fence class + * @base: base fence class * @child_list:membership in sync_timeline.child_list_head * @active_list: membership in sync_timeline.active_list_head - * @signaled_list: membership in temporary signaled_list on stack - * @fence: sync_fence to which the sync_pt belongs - * @pt_list: membership in sync_fence.pt_list_head - * @status:1: signaled, 0:active, <0: error - * @timestamp: time which sync_pt status transitioned from active to - * signaled or error. */ struct sync_pt { struct fence base; @@ -144,12 +138,11 @@ struct sync_fence_cb { * @file: file representing this fence * @kref: reference count on fence. * @name: name of sync_fence. Useful for debugging - * @pt_list_head: list of sync_pts in the fence. immutable once fence - * is created - * @status:0: signaled, >0:active, <0: error - * - * @wq:wait queue for fence signaling * @sync_fence_list: membership in global fence list + * @num_fences number of sync_pts in the fence + * @wq:wait queue for fence signaling + * @status:0: signaled, >0:active, <0: error + * @cbs: sync_pts callback information */ struct sync_fence { struct file *file; @@ -172,9 +165,8 @@ typedef void (*sync_callback_t)(struct sync_fence *fence, /** * struct sync_fence_waiter - metadata for asynchronous waiter on a fence - * @waiter_list: membership in sync_fence.waiter_list_head + * @work: wait_queue for the fence waiter * @callback: function pointer to call when fence signals - * @callback_data: pointer to pass to @callback */ struct sync_fence_waiter { wait_queue_t work; @@ -200,7 +192,8 @@ static inline void sync_fence_waiter_init(struct sync_fence_waiter *waiter, * * Creates a new sync_timeline which will use the implementation specified by * @ops. @size bytes will be allocated allowing for implementation specific - * data to be kept after the generic sync_timeline struct. + * data to be kept after the generic sync_timeline struct. Returns the + * sync_timeline object or NULL in case of error. */ struct sync_timeline *sync_timeline_create(const struct sync_timeline_ops *ops, int size, const char *name); @@ -231,7 +224,8 @@ void sync_timeline_signal(struct sync_timeline *obj); * * Creates a new sync_pt as a child of @parent. @size bytes will be * allocated allowing for implementation specific data to be kept after - * the generic sync_timeline struct. + * the generic sync_timeline struct. Returns the sync_pt object or + * NULL in case of error. */ struct sync_pt *sync_pt_create(struct sync_timeline *parent, int size); @@ -275,7 +269,8 @@ struct sync_fence *sync_fence_create_dma(const char *name, struct fence *pt); * @b: fence b * * Creates a new fence which contains copies of all the sync_pts in both - * @a and @b. @a and @b remain valid, independent fences. + * @a and @b. @a and @b remain valid, independent fences. Returns the + * new merged fence or NULL in case of error. */ struct sync_fence *sync_fence_merge(const char *name, struct sync_fence *a, struct sync_fence *b); @@ -285,7 +280,7 @@ struct sync_fence *sync_fence_merge(const char *name, * @fd:fd referencing a fence * * Ensures @fd references a valid fence, increments the refcount of the backing - * file, and returns the fence. + * file, and returns the fence. Returns the fence or NULL in case of error. */ struct sync_fence *sync_fence_fdget(int fd); @@ -313,10 +308,10 @@ void sync_fence_install(struct sync_fence *fence, int fd); * @fence: fence to wait on * @waiter:waiter callback struck * - * Returns 1 if @fence has already signaled. - * * Registers a callback to be called when @fence signals or has an error. * @waiter should be initialized with sync_fence_waiter_init(). + * + * Returns 1 if @fence has already signaled, 0 if not or <0 if error. */ int sync_fence_wait_async(struct sync_fence *fence, struct sync_fence_waiter *waiter); @@ -326,11 +321,11 @@ int sync_fence_wait_async(struct
[RFC 00/29] De-stage android's sync framework
From: Gustavo PadovanThis patch series de-stage the sync framework, and in order to accomplish that a bunch of cleanups/improvements on the sync and fence were made. The sync framework contained some abstractions around struct fence and those were removed in the de-staging process among other changes: Userspace visible changes - * The sw_sync file was moved from /dev/sw_sync to /sync/sw_sync. No other change. Kernel API changes -- * struct sync_timeline is now struct fence_timeline * sync_timeline_ops is now fence_timeline_ops and they now carry struct fence as parameter instead of struct sync_pt * a .cleanup() fence op was added to allow sync_fence to run a cleanup when the fence_timeline is destroyed * added fence_add_used_data() to pass a private point to struct fence. This pointer is sent back on the .cleanup op. * The sync timeline function were moved to be fence_timeline functions: - sync_timeline_create() -> fence_timeline_create() - sync_timeline_get() -> fence_timeline_get() - sync_timeline_put() -> fence_timeline_put() - sync_timeline_destroy() -> fence_timeline_destroy() - sync_timeline_signal() -> fence_timeline_signal() * sync_pt_create() was replaced be fence_create_on_timeline() Internal changes * fence_timeline_ops was removed in favor of direct use fence_ops * fence default functions were created for fence_ops * removed structs sync_pt, sw_sync_timeline and sw_sync_pt Gustavo Padovan (29): staging/android: fix sync framework documentation staging/android: fix checkpatch warning staging/android: rename sync_fence_release staging/android: rename 'android_fence' to 'sync_fence' staging/android: remove not used sync_timeline ops staging/android: create a 'sync' dir for debugfs information staging/android: move sw_sync file to debugfs file staging/android: Remove WARN_ON_ONCE when releasing sync_fence staging/android: rename struct sync_fence's variables to 'sync_fence' staging/android: rename 'sync_pt' to 'fence' in struct sync_fence_cb dma-buf/fence: move sync_timeline to fence_timeline staging/android: remove struct sync_pt dma-buf/fence: create fence_default_enable_signaling() dma-buf/fence: create fence_default_release() dma-buf/fence: create fence_default_get_driver_name() dma-buf/fence: create fence_default_timeline_name() dma-buf/fence: store last signaled value on fence timeline dma-buf/fence: create default .fence_value_str() and .timeline_value_str() dma-buf/fence: create fence_default_fill_driver_data() dma-buf/fence: remove fence_timeline_ops dma-buf/fence: add fence_create_on_timeline() staging/android: remove sync_pt_create() staging/android: remove sw_sync_timeline and sw_sync_pt dma-buf/fence: add debug to fence timeline dma-buf/fence: remove unused var from fence_timeline_signal() dma-buf/fence: remove pointless fence_timeline_signal at destroy phase dma-buf/fence: add .cleanup() callback staging/android: use .cleanup() to interrupt any sync_fence waiter dma-buf/fence: de-stage sync framework drivers/Kconfig| 2 + drivers/dma-buf/Kconfig| 22 + drivers/dma-buf/Makefile | 4 +- drivers/dma-buf/fence.c| 333 ++ drivers/dma-buf/fence_debug.c | 128 drivers/dma-buf/sw_sync.c | 65 ++ drivers/dma-buf/sync.c | 527 +++ drivers/dma-buf/sync_debug.c | 279 drivers/staging/android/Kconfig| 28 - drivers/staging/android/Makefile | 2 - drivers/staging/android/sw_sync.c | 260 drivers/staging/android/sync.c | 732 - drivers/staging/android/sync.h | 366 --- drivers/staging/android/sync_debug.c | 256 --- include/linux/fence.h | 77 +++ .../staging/android => include/linux}/sw_sync.h| 30 +- include/linux/sync.h | 201 ++ include/trace/events/fence.h | 18 + .../android/trace => include/trace/events}/sync.h | 41 +- .../android/uapi => include/uapi/linux}/sw_sync.h | 0 .../android/uapi => include/uapi/linux}/sync.h | 0 21 files changed, 1672 insertions(+), 1699 deletions(-) create mode 100644 drivers/dma-buf/Kconfig create mode 100644 drivers/dma-buf/fence_debug.c create mode 100644 drivers/dma-buf/sw_sync.c create mode 100644 drivers/dma-buf/sync.c create mode 100644 drivers/dma-buf/sync_debug.c delete mode 100644 drivers/staging/android/sw_sync.c delete mode 100644 drivers/staging/android/sync.c delete mode 100644
[Bug 93727] [Regression] [r600g] Core profile is 3.2 instead of 3.3 in Big Endian PPC
https://bugs.freedesktop.org/show_bug.cgi?id=93727 Oded Gabbay changed: What|Removed |Added Summary|[Regression] Core profile |[Regression] [r600g] Core |is 3.2 instead of 3.3 in|profile is 3.2 instead of |Big Endian PPC |3.3 in Big Endian PPC -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/67ca8642/attachment.html>
[Bug 93727] [Regression] Core profile is 3.2 instead of 3.3 in Big Endian PPC
https://bugs.freedesktop.org/show_bug.cgi?id=93727 Oded Gabbay changed: What|Removed |Added Hardware|Other |PowerPC OS|All |Linux (All) -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/49b5471e/attachment.html>
[Bug 93727] [Regression] Core profile is 3.2 instead of 3.3 in Big Endian PPC
https://bugs.freedesktop.org/show_bug.cgi?id=93727 --- Comment #1 from Oded Gabbay --- Created attachment 121064 --> https://bugs.freedesktop.org/attachment.cgi?id=121064=edit glxinfo for mesa 11.0.8 -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/add8229a/attachment.html>
[Bug 93727] [Regression] Core profile is 3.2 instead of 3.3 in Big Endian PPC
https://bugs.freedesktop.org/show_bug.cgi?id=93727 Bug ID: 93727 Summary: [Regression] Core profile is 3.2 instead of 3.3 in Big Endian PPC Product: Mesa Version: 11.0 Hardware: Other OS: All Status: NEW Severity: normal Priority: medium Component: Drivers/Gallium/r600 Assignee: dri-devel at lists.freedesktop.org Reporter: oded.gabbay at gmail.com QA Contact: dri-devel at lists.freedesktop.org Created attachment 121063 --> https://bugs.freedesktop.org/attachment.cgi?id=121063=edit glxinfo for mesa 10.3.2 In mesa 11.0.8, the core profile reported by mesa for r600 gallium driver is 3.2, while in mesa 10.3.2 the core profile was 3.3 This is because the ARB_texture_rgb10_a2ui extension is reported to be unsupported by the r600 driver -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/4d19df61/attachment-0001.html>
[Bug 93713] System hangs (beomes totaly unresponsive) when trying to use hybrid graphics with ATI 7730M videocard
https://bugs.freedesktop.org/show_bug.cgi?id=93713 --- Comment #2 from Victor Petrenko --- (In reply to Alex Deucher from comment #1) > Does booting with: > radeon.runpm=0 > on the kernel command line in grub help? Nope. Same behavior. A couple of seconds i can see things running but then everything becomes very slow and in another second whole system freezes. Funny thing that mouse cursor still works (freezes from time to time but movable), but can't switch to plain terminal by Ctrl+Alt+FX anymore or to do any other action. Another thing that fan starts running with crazy speed, so it means that in the background something happens and makes videocard/processor rather loaded. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/2a8329ed/attachment.html>
[Bug 93721] Tonga [drm:amdgpu_vm_init [amdgpu]] *ERROR* Cannot allocate memory for page table array
https://bugs.freedesktop.org/show_bug.cgi?id=93721 --- Comment #6 from Andy Furniss --- (In reply to Ernst Sjöstrand from comment #4) > I think I also had a UVD related hang on Fiji with Powerplay when setting > EnableLinuxHWVideoDecode = 1 in /etc/adobe/mms.cfg and watching flash video. > Not sure if my Firefox settings affect the result, but I had 100% hang rate. > Couldn't find any logs messages though. On older powerplays I could get a logless uvd lock up - not on current drm-next yet (it took many hours to provoke). I can trigger a different one with mpv - to get logging you need to wait a few minutes before sysrq as the logging comes from the kernel hung task timeout. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/178741da/attachment.html>
[Bug 93721] Tonga [drm:amdgpu_vm_init [amdgpu]] *ERROR* Cannot allocate memory for page table array
https://bugs.freedesktop.org/show_bug.cgi?id=93721 --- Comment #5 from Andy Furniss --- (In reply to Michel Dänzer from comment #3) > Created attachment 121055 [details] [review] > drm/amdgpu: Use drm_calloc_large for VM page_tables array > > Does this patch help? Running now - OK so far, but then it took some time/luck to show up on unpatched. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/bc97638b/attachment.html>
[Bug 91880] Radeonsi on Grenada cards (r9 390) exceptionally unstable and poorly performing
https://bugs.freedesktop.org/show_bug.cgi?id=91880 --- Comment #57 from Andy Furniss --- I have different h/w from you (TONGA). Forcing high can help me but be aware that for me at least it may change back to auto as soon as some display change happens eg. Coming out of dpms or changing a mode. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/00f08a04/attachment.html>
[Bug 91880] Radeonsi on Grenada cards (r9 390) exceptionally unstable and poorly performing
https://bugs.freedesktop.org/show_bug.cgi?id=91880 --- Comment #56 from Julian --- (In reply to Thomas DEBESSE from comment #55) > Hi, I made some tests, I discovered that my R9 390X works very well if I > never load the "auto" `power_dpm_force_performance_level` profile, both > "low" and "high" works. Also, both `power_dpm_state` "balanced", "battery", > "performance" works. > > ... Thank you for that. It seems like my system reacts the same way - I've re-enabled DPM and set the perf level to something that isn't auto. It's not crashed on me for about an hour now which is better than it did before. I've also tried your tool - the service doesn't actually set the dpm parameters to 'low' and 'battery' for me. Maybe some issue with permissions involved. But dpm-query works fine and it great for convenience. Thanks for that as well. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/1edc7d47/attachment-0001.html>
[PATCH] drm: omap dss: add missing includes
The omapdrm dss driver currently fails to build in some configurations when the pinctrl and seq_print declarations are not visible: omapdrm/dss/dss.c:1268:2: error: implicit declaration of function 'pinctrl_pm_select_sleep_state' [-Werror=implicit-function-declaration] omapdrm/dss/dss.c:1277:2: error: implicit declaration of function 'pinctrl_pm_select_default_state' [-Werror=implicit-function-declaration] omapdrm/dss/hdmi_wp.c:26:2: error: implicit declaration of function 'seq_printf' [-Werror=implicit-function-declaration] omapdrm/dss/hdmi_pll.c:30:2: error: implicit declaration of function 'seq_printf' [-Werror=implicit-function-declaration] omapdrm/dss/hdmi_phy.c:34:2: error: implicit declaration of function 'seq_printf' [-Werror=implicit-function-declaration] This adds the appropriate include statements. Signed-off-by: Arnd Bergmann Fixes: 9960aa7cb58c ("drm/omap: move omapdss & displays under omapdrm") --- Found on ARM randconfig builds. I assume there are also configurations in which this is not needed because the headers get included through other headers, and I have not investigated exactly what options cause this as the fix seems obvious and harmless. diff --git a/drivers/gpu/drm/omapdrm/dss/dss.c b/drivers/gpu/drm/omapdrm/dss/dss.c index f95ff319e68e..839b1b6bdbe4 100644 --- a/drivers/gpu/drm/omapdrm/dss/dss.c +++ b/drivers/gpu/drm/omapdrm/dss/dss.c @@ -37,6 +37,7 @@ #include #include #include +#include #include #include #include diff --git a/drivers/gpu/drm/omapdrm/dss/hdmi_phy.c b/drivers/gpu/drm/omapdrm/dss/hdmi_phy.c index 1f5d19c119ce..a872721a03a2 100644 --- a/drivers/gpu/drm/omapdrm/dss/hdmi_phy.c +++ b/drivers/gpu/drm/omapdrm/dss/hdmi_phy.c @@ -13,6 +13,8 @@ #include #include #include +#include + #include #include "dss.h" diff --git a/drivers/gpu/drm/omapdrm/dss/hdmi_pll.c b/drivers/gpu/drm/omapdrm/dss/hdmi_pll.c index 06e23a7c432c..f1015e8b8267 100644 --- a/drivers/gpu/drm/omapdrm/dss/hdmi_pll.c +++ b/drivers/gpu/drm/omapdrm/dss/hdmi_pll.c @@ -16,6 +16,7 @@ #include #include #include +#include #include diff --git a/drivers/gpu/drm/omapdrm/dss/hdmi_wp.c b/drivers/gpu/drm/omapdrm/dss/hdmi_wp.c index 7c544bc56fb5..753ac305d32a 100644 --- a/drivers/gpu/drm/omapdrm/dss/hdmi_wp.c +++ b/drivers/gpu/drm/omapdrm/dss/hdmi_wp.c @@ -14,6 +14,7 @@ #include #include #include +#include #include #include "dss.h"
Lockdep warning when using REGCACHE_RBTREE
On Fri, Jan 15, 2016 at 10:45:41AM +0100, Peter Zijlstra wrote: > So _regmap_write() does: map->lock(map->lock_arg) > Which isn't very enlightening, since that can be a mutex or a spinlock, > the above strongly suggests spinlock though. > Looking at __regmap_init(), this seems to depend on: > (bus && bus->fast_io) || config->fast_io > now, afaict, regmap_mmio is used in this case, which has .fast_io = > true. > So yeah, fail. Indeed, that'd do it. It hadn't occurred to me that someone would be using MMIO with an rbtree cache. -- next part -- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 473 bytes Desc: not available URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/1926ba49/attachment.sig>
linux-4.4 bisected: kwin5 stuck on kde5 loading screen with radeon
Hi, since kernel 4.4 I'm unable to login to kde5 desktop (on openSUSE Tumbleweed). There's a screen with progressbar showing the startup, which normally fades away after reaching 100%. But with kernel 4.4, the progress gets stuck somewhere between 1/2 and 3/4 (not always the same). Top shows that kwin is using few % of CPU's but mostly sleeps in poll(). When I kill it from another console, I see that everything has actually started up, just the progressbar screen was obscuring it. The windows obviously don't have decorations etc. Starting kwin manually again shows me again the progressbar screen at the same position. I have suspected that kwin is waiting for some event, but nevertheless tried bisecting the kernel between 4.3 and 4.4, which lead to: # first bad commit: [4dfd64862ff852df7b1198d667dda778715ee88f] drm: Use vblank timestamps to guesstimate how many vblanks were missed I can confirm that 4.4 works if I revert the following commits: 63154ff230fc9255cc507af6277cd181943c50a1 "drm/amdgpu: Fixup hw vblank counter/ts for new drm_update_vblank_count() (v3)" d1145ad1e41b6c33758a856163198cb53bb96a50 "drm/radeon: Fixup hw vblank counter/ts for new drm_update_vblank_count() (v2)" 31ace027c9f1f8e0a2b09bbf961e4db7b1f6cf19 "drm: Don't zero vblank timestamps from the irq handler" ac0567a4b132fa66e3edf3f913938af9daf7f916 "drm: Add DRM_DEBUG_VBL()" 4dfd64862ff852df7b1198d667dda778715ee88f "drm: Use vblank timestamps to guesstimate how many vblanks were missed" All clean reverts, just needs some fixup on top to use abs() instead of abs64() due to 79211c8ed19c055ca105502c8733800d442a0ae6. Unfortunately I don't know if this is a kernel problem or kwin problem. I tried to CC maintainers of both, advices what to try or what info to provide welcome. The card is "CAICOS" with 1GB memory. Thanks, Vlastimil
DRM support in Android
On Fri, Jan 15, 2016 at 09:35:27AM +0800, Chih-Wei Huang wrote: > 2016-01-09 16:37 GMT+08:00 vijay kumar : > > Thanks Greg .You Helped me a lot. > > > > On Thu, Jan 7, 2016 at 10:52 PM, Greg Hackmann > > wrote: > >> > >> On Tue, Jan 5, 2016 at 12:06 AM, vijay kumar > >> wrote: > >>> > >>> Hii all, > >>> I want to know some information regarding DRI and DRM > >>> support in android.Does Android uses DRI drivers in MESA for Direct > >>> rendering. > >> > >> The vendor needs to supply an EGL implementation at a well-known path > >> (https://android.googlesource.com/platform/frameworks/native/+/android-6.0.1_r5/opengl/libs/EGL/Loader.cpp#41). > >> This can be Mesa or a proprietary library. > > Android-x86 is the first open source project > that brought Mesa/DRM to the Android platform. > Refer to: > > http://sourceforge.net/p/android-x86/external_libdrm/ > http://sourceforge.net/p/android-x86/external_mesa/ > http://sourceforge.net/p/android-x86/external_drm_gralloc/ (Drm based > gralloc HAL) > > It's glad to see drm_gralloc is now a part of > AOSP marshmallow release. > Google Pixel C is probably the first (and only?) one > android product that uses it. > > We have a devel group working on that. > If you are interesting, I can invite you to join. Fyi Google just opened up their drm_hwcomposer implementation. Open as in actually open for patches! https://dev.chromium.org/android/contributing-to-drm_hwcomposer Cheers, Daniel -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
[PATCH v2 13/26] drm/fb_cma_helper: Remove implicit call to disable_unused_functions
On Fri, Jan 15, 2016 at 01:13:05AM +0200, Laurent Pinchart wrote: > Hi Maxime, > > Thank you for the patch. > > On Thursday 14 January 2016 16:24:56 Maxime Ripard wrote: > > The drm_fbdev_cma_init function always calls the > > drm_helper_disable_unused_functions. Since it's part of the usual probe > > process, all the drivers using that helper will end up having their encoder > > and CRTC disable functions called at probe if their device has not been > > reported as enabled. > > > > This could be fixed by reading out from the registers the current state of > > the device if it is enabled, but even that will not handle the case where > > the device is actually disabled. > > > > Moreover, the drivers using the atomic modesetting expect that their enable > > and disable callback to be called when the device is already enabled or > > disabled (respectively). > > > > We can however fix this issue by moving the call to > > drm_helper_disable_unused_functions out of drm_fbdev_cma_init and make the > > drivers needing it (all the drivers calling drm_fbdev_cma_init and not > > using the atomic modesetting) explicitly call it. > > I'd rather add it to all drivers that call drm_fbdev_cma_init(). All the > atomic ones must have special code to cope with it that could be rendered > useless by the removal of the drm_helper_disable_unused_functions() call. > That > code should be removed too, and it would be easier to check drivers one by > one > and fixing them individually (outside of this patch series, unless you insist > ;-)) when removing the explicit drm_helper_disable_unused_functions() call. I had the same thought, but figured there's really no good reason ever to do this. I suspect most of that disable_unused_function stuff we have all over is supreme cargo-cult anyway ;-) > Other than that the patch looks fine to me. So went ahead and applied to drm-misc. -Daniel > > > Signed-off-by: Maxime Ripard > > --- > > drivers/gpu/drm/drm_fb_cma_helper.c | 3 --- > > drivers/gpu/drm/imx/imx-drm-core.c | 1 + > > drivers/gpu/drm/sti/sti_drv.c | 1 + > > drivers/gpu/drm/tilcdc/tilcdc_drv.c | 1 + > > 4 files changed, 3 insertions(+), 3 deletions(-) > > > > diff --git a/drivers/gpu/drm/drm_fb_cma_helper.c > > b/drivers/gpu/drm/drm_fb_cma_helper.c index c19a62561183..daa98d881142 > > 100644 > > --- a/drivers/gpu/drm/drm_fb_cma_helper.c > > +++ b/drivers/gpu/drm/drm_fb_cma_helper.c > > @@ -348,9 +348,6 @@ struct drm_fbdev_cma *drm_fbdev_cma_init(struct > > drm_device *dev, > > > > } > > > > - /* disable all the possible outputs/crtcs before entering KMS mode */ > > - drm_helper_disable_unused_functions(dev); > > - > > ret = drm_fb_helper_initial_config(helper, preferred_bpp); > > if (ret < 0) { > > dev_err(dev->dev, "Failed to set initial hw configuration.\n"); > > diff --git a/drivers/gpu/drm/imx/imx-drm-core.c > > b/drivers/gpu/drm/imx/imx-drm-core.c index 7b990b4e96d2..e1db57791fc9 > > 100644 > > --- a/drivers/gpu/drm/imx/imx-drm-core.c > > +++ b/drivers/gpu/drm/imx/imx-drm-core.c > > @@ -312,6 +312,7 @@ static int imx_drm_driver_load(struct drm_device *drm, > > unsigned long flags) dev_warn(drm->dev, "Invalid legacyfb_depth. > > Defaulting to 16bpp\n"); legacyfb_depth = 16; > > } > > + drm_helper_disable_unused_functions(drm); > > imxdrm->fbhelper = drm_fbdev_cma_init(drm, legacyfb_depth, > > drm->mode_config.num_crtc, MAX_CRTC); > > if (IS_ERR(imxdrm->fbhelper)) { > > diff --git a/drivers/gpu/drm/sti/sti_drv.c b/drivers/gpu/drm/sti/sti_drv.c > > index 1469987949d8..506b5626f3ed 100644 > > --- a/drivers/gpu/drm/sti/sti_drv.c > > +++ b/drivers/gpu/drm/sti/sti_drv.c > > @@ -160,6 +160,7 @@ static int sti_load(struct drm_device *dev, unsigned > > long flags) > > > > drm_mode_config_reset(dev); > > > > + drm_helper_disable_unused_functions(dev); > > drm_fbdev_cma_init(dev, 32, > >dev->mode_config.num_crtc, > >dev->mode_config.num_connector); > > diff --git a/drivers/gpu/drm/tilcdc/tilcdc_drv.c > > b/drivers/gpu/drm/tilcdc/tilcdc_drv.c index 876cad58b1f9..24be31d69701 > > 100644 > > --- a/drivers/gpu/drm/tilcdc/tilcdc_drv.c > > +++ b/drivers/gpu/drm/tilcdc/tilcdc_drv.c > > @@ -294,6 +294,7 @@ static int tilcdc_load(struct drm_device *dev, unsigned > > long flags) break; > > } > > > > + drm_helper_disable_unused_functions(dev); > > priv->fbdev = drm_fbdev_cma_init(dev, bpp, > > dev->mode_config.num_crtc, > > dev->mode_config.num_connector); > > -- > Regards, > > Laurent Pinchart > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
[PATCH v3 1/3] drm: add generic zpos property
On Fri, Jan 15, 2016 at 10:09:14AM +0100, Marek Szyprowski wrote: > Hello, > > On 2016-01-14 11:46, Ville Syrjälä wrote: > >On Tue, Jan 12, 2016 at 02:39:18PM +0100, Marek Szyprowski wrote: > >>This patch adds support for generic plane's zpos property property with > >>well-defined semantics: > >>- added zpos properties to drm core and plane state structures > >>- added helpers for normalizing zpos properties of given set of planes > >>- well defined semantics: planes are sorted by zpos values and then plane > >> id value if zpos equals > >> > >>Normalized zpos values are calculated automatically when generic > >>muttable zpos property has been initialized. Drivers can simply use > >>plane_state->normalized_zpos in their atomic_check and/or plane_update > >>callbacks without any additional calls to DRM core. > >> > >>Signed-off-by: Marek Szyprowski > >>--- > >> Documentation/DocBook/gpu.tmpl | 14 - > >> drivers/gpu/drm/drm_atomic.c| 4 ++ > >> drivers/gpu/drm/drm_atomic_helper.c | 116 > >> > >> drivers/gpu/drm/drm_crtc.c | 53 > >> include/drm/drm_crtc.h | 14 + > >> 5 files changed, 199 insertions(+), 2 deletions(-) > >> > >>diff --git a/Documentation/DocBook/gpu.tmpl b/Documentation/DocBook/gpu.tmpl > >>index 6c6e81a9eaf4..f6b7236141b6 100644 > >>--- a/Documentation/DocBook/gpu.tmpl > >>+++ b/Documentation/DocBook/gpu.tmpl > >>@@ -2004,7 +2004,7 @@ void intel_crt_init(struct drm_device *dev) > >>Description/Restrictions > >> > >> > >>- DRM > >>+ DRM > >>Generic > >>ârotationâ > >>BITMASK > >>@@ -2256,7 +2256,7 @@ void intel_crt_init(struct drm_device *dev) > >>property to suggest an Y offset for a connector > >> > >> > >>- Optional > >>+ Optional > >>âscaling modeâ > >>ENUM > >>{ "None", "Full", "Center", "Full aspect" } > >>@@ -2280,6 +2280,16 @@ void intel_crt_init(struct drm_device *dev) > >>TBD > >> > >> > >>+"zpos" > >>+ RANGE > >>+ Min=0, Max=255 > >>+ Plane > >>+ Plane's 'z' position during blending (0 for > >>background, 255 for frontmost). > >>+ If two planes assigned to same CRTC have equal zpos values, the > >>plane with higher plane > >>+ id is treated as closer to front. Can be IMMUTABLE if driver > >>doesn't support changing > >>+ planes' order. > >I don't think this is going to work very well. Mixing the same range > >of 0-255 for all planes, with potentially some of them being > >IMMUTABLE for sure won't end well, or at least won't allow userspace to > >see if there are any constraints between the zpos of the planes. > > > >So I think what we should do is let the driver specify the valid range, > >and get rid of the obj id based conflict resolution in favor of just > >rejecting conflicts outright. In cases where you can't move the planes > >between crtcs, the driver ought to specify the range based on the > >number of planes present on the crtc. If planes can be moved betweens > >crtcs the range obviously needs to be larger to accomodate all the > >possible planes on the crtc. > > > >Eg. on Intel VLV/CHV we could have the following setup: > >primary zpos 0-2 > >sprite 0 zpos 0-2 > >sprite 1 zpos 0-2 > >cursor zpos 3 > > > >That makes it very clear the curso is always on top, and the other > >planes can be rearranged more or less freely. These planes can't be > >moved between crtcs, so each there's an identical set of planes for > >each crtc. > > > >On old Intel hw (gen2/3) we could have something like: > >plane A zpos 0-3 > >plane B zpos 0-3 > >plane C zpos 0-3 > >overlay zpos 0-3 > >cursor B zpos 4 > >cursor A zpos 5 > > > >Most of these planes can be moved between crtcs, and IIRC there > >are probably more constraints on exactly how they can be stacked, but > >this is at least fairly close to the truth. Again the cursors are always > >on top, and in this case the order between the two cursor planes is also > >fixed. > > I wasn't aware of a hardware, which has limited configuration of zpos only > to some planes. I thought only about 2 cases: either completely configurable > planes arrangement, or planes fixed to some hw dependent order. I see no > problem to let drivers to define their own limits for mutable zpos property. > > Now the question is weather we should allow to set the non-zero minimal > value > for mutable zpos? I can imagine that there might be a hardware, which has > fixed background plane and a few configurable overlay planes. I assume that > in such case, the calculated normalized_zpos should still start from zero. The usual approach is to switch the property from a global one in dev->mode_config.*_prop to a per-object one in e.g. plane->zpos_prop. We can still register the name, but have different limits/types. That way you could register a global mutable zpos with the range 0-3 and an immutable zpos with values 4 or 5 for cursors.
[RFC 00/29] De-stage android's sync framework
On Fri, 2016-01-15 at 12:55 -0200, Gustavo Padovan wrote: > From: Gustavo Padovan > > This patch series de-stage the sync framework, and in order to accomplish that > a bunch of cleanups/improvements on the sync and fence were made. Perhaps add/update a MAINTAINERS entry too?
Lockdep warning when using REGCACHE_RBTREE
On 2016-01-15 08:28, Mark Brown wrote: > On Thu, Jan 14, 2016 at 05:14:47PM -0800, Stefan Agner wrote: > >> On a slightly other topic, I question whether REGCACHE_RBTREE is the >> right cache type for the DCU DRM driver. The driver has uses a regmap >> area of 1144 32-bit registers, the most space is used by the layer >> configuration registers which are 0x40 apart and 0x0-0x20 for each layer >> are actually used (hence somewhat above 50%). > >> Would FLAT be the better cache type? > > Yes, and if it's a MMIO device the performance of a flat cache is more > in line with the device performance. Thanks for confirming that. I will switch to REGCACHE_FLAT then, I found a second driver with the very same issue, also a MMIO mapped device: drivers/pwm/pwm-fsl-ftm.c... -- Stefan
Lockdep warning when using REGCACHE_RBTREE
On Thu, Jan 14, 2016 at 02:30:50PM -0800, Stefan Agner wrote: > Hi Mark, > > I currently work on the DCU DRM driver (drivers/gpu/drm/fsl-dcu/) on a > Linux 4.4 kernel. With CONFIG_LOCKDEP enabled I get the following > warning on startup: > > [1.327284] [ cut here ] > [1.332010] WARNING: CPU: 0 PID: 1 at kernel/locking/lockdep.c:2755 > lockdep_trace_alloc+0x120/0x124() > [1.341358] DEBUG_LOCKS_WARN_ON(irqs_disabled_flags(flags)) > [1.521744] [<80375308>] (_regmap_write) from [<80376760>] > (regmap_write+0x48/0x68) > [1.535348] [<80376718>] (regmap_write) from [<803538e8>] > (fsl_dcu_drm_crtc_create+0x98/0xe8) > [1.549824] [<80353850>] (fsl_dcu_drm_crtc_create) from [<80352df0>] > (fsl_dcu_drm_modeset_init+0x5c/0xfc) > The comment in __lockdep_trace_alloc says: > "Oi! Can't be having __GFP_FS allocations with IRQs disabled.". So _regmap_write() does: map->lock(map->lock_arg) Which isn't very enlightening, since that can be a mutex or a spinlock, the above strongly suggests spinlock though. Looking at __regmap_init(), this seems to depend on: (bus && bus->fast_io) || config->fast_io now, afaict, regmap_mmio is used in this case, which has .fast_io = true. So yeah, fail.
[PATCH v3 1/3] drm: add generic zpos property
Hello, On 2016-01-14 11:46, Ville Syrjälä wrote: > On Tue, Jan 12, 2016 at 02:39:18PM +0100, Marek Szyprowski wrote: >> This patch adds support for generic plane's zpos property property with >> well-defined semantics: >> - added zpos properties to drm core and plane state structures >> - added helpers for normalizing zpos properties of given set of planes >> - well defined semantics: planes are sorted by zpos values and then plane >>id value if zpos equals >> >> Normalized zpos values are calculated automatically when generic >> muttable zpos property has been initialized. Drivers can simply use >> plane_state->normalized_zpos in their atomic_check and/or plane_update >> callbacks without any additional calls to DRM core. >> >> Signed-off-by: Marek Szyprowski >> --- >> Documentation/DocBook/gpu.tmpl | 14 - >> drivers/gpu/drm/drm_atomic.c| 4 ++ >> drivers/gpu/drm/drm_atomic_helper.c | 116 >> >> drivers/gpu/drm/drm_crtc.c | 53 >> include/drm/drm_crtc.h | 14 + >> 5 files changed, 199 insertions(+), 2 deletions(-) >> >> diff --git a/Documentation/DocBook/gpu.tmpl b/Documentation/DocBook/gpu.tmpl >> index 6c6e81a9eaf4..f6b7236141b6 100644 >> --- a/Documentation/DocBook/gpu.tmpl >> +++ b/Documentation/DocBook/gpu.tmpl >> @@ -2004,7 +2004,7 @@ void intel_crt_init(struct drm_device *dev) >> Description/Restrictions >> >> >> -DRM >> +DRM >> Generic >> ârotationâ >> BITMASK >> @@ -2256,7 +2256,7 @@ void intel_crt_init(struct drm_device *dev) >> property to suggest an Y offset for a connector >> >> >> -Optional >> +Optional >> âscaling modeâ >> ENUM >> { "None", "Full", "Center", "Full aspect" } >> @@ -2280,6 +2280,16 @@ void intel_crt_init(struct drm_device *dev) >> TBD >> >> >> + "zpos" >> +RANGE >> +Min=0, Max=255 >> +Plane >> +Plane's 'z' position during blending (0 for >> background, 255 for frontmost). >> +If two planes assigned to same CRTC have equal zpos values, the >> plane with higher plane >> +id is treated as closer to front. Can be IMMUTABLE if driver >> doesn't support changing >> +planes' order. > I don't think this is going to work very well. Mixing the same range > of 0-255 for all planes, with potentially some of them being > IMMUTABLE for sure won't end well, or at least won't allow userspace to > see if there are any constraints between the zpos of the planes. > > So I think what we should do is let the driver specify the valid range, > and get rid of the obj id based conflict resolution in favor of just > rejecting conflicts outright. In cases where you can't move the planes > between crtcs, the driver ought to specify the range based on the > number of planes present on the crtc. If planes can be moved betweens > crtcs the range obviously needs to be larger to accomodate all the > possible planes on the crtc. > > Eg. on Intel VLV/CHV we could have the following setup: > primary zpos 0-2 > sprite 0 zpos 0-2 > sprite 1 zpos 0-2 > cursor zpos 3 > > That makes it very clear the curso is always on top, and the other > planes can be rearranged more or less freely. These planes can't be > moved between crtcs, so each there's an identical set of planes for > each crtc. > > On old Intel hw (gen2/3) we could have something like: > plane A zpos 0-3 > plane B zpos 0-3 > plane C zpos 0-3 > overlay zpos 0-3 > cursor B zpos 4 > cursor A zpos 5 > > Most of these planes can be moved between crtcs, and IIRC there > are probably more constraints on exactly how they can be stacked, but > this is at least fairly close to the truth. Again the cursors are always > on top, and in this case the order between the two cursor planes is also > fixed. I wasn't aware of a hardware, which has limited configuration of zpos only to some planes. I thought only about 2 cases: either completely configurable planes arrangement, or planes fixed to some hw dependent order. I see no problem to let drivers to define their own limits for mutable zpos property. Now the question is weather we should allow to set the non-zero minimal value for mutable zpos? I can imagine that there might be a hardware, which has fixed background plane and a few configurable overlay planes. I assume that in such case, the calculated normalized_zpos should still start from zero. > I did originally have the same obj id based sorting idea (and even > posted some kind of a patch for it IIRC) but that was before atomic > existed, so there was a real need to allow reordering the planes with > just a single setplane ioctl call. With atomic I don't see any real > benefit from it the obj id based sorting, and as I've noted there are > definitely downsides to it. What are the downsides of using obj id as additional sorting criteria? It solves all the ambiguities and
DRM support in Android
2016-01-09 16:37 GMT+08:00 vijay kumar : > Thanks Greg .You Helped me a lot. > > On Thu, Jan 7, 2016 at 10:52 PM, Greg Hackmann > wrote: >> >> On Tue, Jan 5, 2016 at 12:06 AM, vijay kumar wrote: >>> >>> Hii all, >>> I want to know some information regarding DRI and DRM >>> support in android.Does Android uses DRI drivers in MESA for Direct >>> rendering. >> >> The vendor needs to supply an EGL implementation at a well-known path >> (https://android.googlesource.com/platform/frameworks/native/+/android-6.0.1_r5/opengl/libs/EGL/Loader.cpp#41). >> This can be Mesa or a proprietary library. Android-x86 is the first open source project that brought Mesa/DRM to the Android platform. Refer to: http://sourceforge.net/p/android-x86/external_libdrm/ http://sourceforge.net/p/android-x86/external_mesa/ http://sourceforge.net/p/android-x86/external_drm_gralloc/ (Drm based gralloc HAL) It's glad to see drm_gralloc is now a part of AOSP marshmallow release. Google Pixel C is probably the first (and only?) one android product that uses it. We have a devel group working on that. If you are interesting, I can invite you to join. -- Chih-Wei Android-x86 project http://www.android-x86.org
[PATCH 5/5] drm: Enable markdown^Wasciidoc for gpu.tmpl
On Thu, 14 Jan 2016, Jonathan Corbet wrote: > On Thu, 14 Jan 2016 22:03:26 +0200 > Jani Nikula wrote: > >> What if we added support for some markup language as an alternative to >> DocBook for the high level documentation? What if we taught kernel-doc >> to output said markup natively, and included those generated pieces into >> the high level documentation using the markup's own include directives? >> At least AsciiDoc and reStructuredText support this. > > That is kind of what I've been thinking. I think we could dispense with > docbook entirely, simplifying the toolchain and making the template files > easier to read and edit. Something like that would also make it easy to > keep the regular .txt documents in a structured form and to integrate them > into the "formatted" documents if it makes sense. Thanks, this is enough encouragement that maybe I'll toy around with this a little more in my, uh, copious free time. > Jani, want to join us at LCA and talk about it? :) Heh, sure I'd *want* to... BR, Jani. -- Jani Nikula, Intel Open Source Technology Center
[PATCH v2 24/26] devicetree: Add olimex vendor prefix
Hi, On Fri, Jan 15, 2016 at 07:41:35AM +0100, Stefan Wahren wrote: > > > Rob Herring hat am 15. Januar 2016 um 04:15 > > geschrieben: > > > > > > On Thu, Jan 14, 2016 at 04:25:07PM +0100, Maxime Ripard wrote: > > > Olimex is an open source hardware boards vendors based in Bulgaria. > > > > > > Signed-off-by: Maxime Ripard > > > --- > > > Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + > > > 1 file changed, 1 insertion(+) > > > > Acked-by: Rob Herring > > > > I don't think we need this twice. > > It's already committed: > > 2193377bdade ("DT: add Olimex to vendor prefixes") Hmm, indeed. Sorry for the noise, I'll drop the commit. Thanks! Maxime -- Maxime Ripard, Free Electrons Embedded Linux, Kernel and Android engineering http://free-electrons.com -- next part -- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 819 bytes Desc: Digital signature URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/b4a4dc1e/attachment.sig>
[PATCH] drm/rockchip/dsi: fix handling mipi_dsi_pixel_format_to_bpp result
Hi Andrzej On 01/14/2016 04:59 PM, Andrzej Hajda wrote: > The function can return negative value so it should be assigned to signed > variable. > > The problem has been detected using patch > scripts/coccinelle/tests/unsigned_lesser_than_zero.cocci. > > Signed-off-by: Andrzej Hajda > --- > drivers/gpu/drm/rockchip/dw-mipi-dsi.c | 3 ++- > 1 file changed, 2 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/rockchip/dw-mipi-dsi.c > b/drivers/gpu/drm/rockchip/dw-mipi-dsi.c > index 7bfe243..f8f8f29 100644 > --- a/drivers/gpu/drm/rockchip/dw-mipi-dsi.c > +++ b/drivers/gpu/drm/rockchip/dw-mipi-dsi.c > @@ -461,10 +461,11 @@ static int dw_mipi_dsi_phy_init(struct dw_mipi_dsi *dsi) > > static int dw_mipi_dsi_get_lane_bps(struct dw_mipi_dsi *dsi) > { > - unsigned int bpp, i, pre; > + unsigned int i, pre; > unsigned long mpclk, pllref, tmp; > unsigned int m = 1, n = 1, target_mbps = 1000; > unsigned int max_mbps = dptdin_map[ARRAY_SIZE(dptdin_map) - 1].max_mbps; > + int bpp; > > bpp = mipi_dsi_pixel_format_to_bpp(dsi->format); > if (bpp < 0) { Reviewed-by: Chris Zhong Thanks
[Bug 93721] Tonga [drm:amdgpu_vm_init [amdgpu]] *ERROR* Cannot allocate memory for page table array
https://bugs.freedesktop.org/show_bug.cgi?id=93721 --- Comment #4 from Ernst Sjöstrand --- I think I also had a UVD related hang on Fiji with Powerplay when setting EnableLinuxHWVideoDecode = 1 in /etc/adobe/mms.cfg and watching flash video. Not sure if my Firefox settings affect the result, but I had 100% hang rate. Couldn't find any logs messages though. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/9265965e/attachment.html>
[Bug 77835] X crash when using xrandr with R9 290X and 7870 for triple head
https://bugs.freedesktop.org/show_bug.cgi?id=77835 --- Comment #6 from Greg Turner --- This looks like bug 79531. Mr. Broemme, if, by any chance, you are still able to repro this problem, check out the patches in that bug, and let us know if they fix the problem for you. And, no need to repeat yourself Michel, I know I still owe the mailing list a respin of that patch -- I didn't give up, just procrastinated. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/58326067/attachment-0001.html>
[PATCH v2 24/26] devicetree: Add olimex vendor prefix
> Rob Herring hat am 15. Januar 2016 um 04:15 geschrieben: > > > On Thu, Jan 14, 2016 at 04:25:07PM +0100, Maxime Ripard wrote: > > Olimex is an open source hardware boards vendors based in Bulgaria. > > > > Signed-off-by: Maxime Ripard > > --- > > Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + > > 1 file changed, 1 insertion(+) > > Acked-by: Rob Herring > I don't think we need this twice. It's already committed: 2193377bdade ("DT: add Olimex to vendor prefixes") Regards Stefan
[Bug 93721] Tonga [drm:amdgpu_vm_init [amdgpu]] *ERROR* Cannot allocate memory for page table array
https://bugs.freedesktop.org/show_bug.cgi?id=93721 --- Comment #3 from Michel Dänzer --- Created attachment 121055 --> https://bugs.freedesktop.org/attachment.cgi?id=121055=edit drm/amdgpu: Use drm_calloc_large for VM page_tables array Does this patch help? -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/2d97146d/attachment.html>
r600/shader: emit tessellation factors to GDS at end of TCS.
Hello Dave, first all the best for your newborn and your whole family! Second: What could be differend between r6xx/r7xx and EG+ (NI, here) that the below fixes the 'gsraytrace' GPU hang on the later but NOT on the former? Any ideas, hints where I could start? r6xx/r7xx do not have any TESS support as we now. So where to start? Disabling some lines of your commit and try? commit 2239f3eaff5c72c4cb1d4a5be97feb4af3d08d25 Author: Dave Airlie Date: Mon Nov 30 15:48:22 2015 +1000 r600/shader: emit tessellation factors to GDS at end of TCS. When we are finished the shader, we read back all the tess factors from LDS and write them to special global memory storage using GDS instructions. This also handles adding NOP when GDS or ENDLOOP end the TCS. Signed-off-by: Dave Airlie Thanks, Dieter
[Bug 91880] Radeonsi on Grenada cards (r9 390) exceptionally unstable and poorly performing
https://bugs.freedesktop.org/show_bug.cgi?id=91880 --- Comment #55 from Thomas DEBESSE --- Hi, I made some tests, I discovered that my R9 390X works very well if I never load the "auto" `power_dpm_force_performance_level` profile, both "low" and "high" works. Also, both `power_dpm_state` "balanced", "battery", "performance" works. So, I wrote a little systemd service that load the "low/battery" profile at startup (just before multi-user.target so it's loaded before the login manager startup. I discovered I can switch `power_dpm_force_performance_level` profile to the value I want and the same for `power_dpm_state` without any crashing, even when an heavy task (like Unigine Valley Benchmark) is running. The fault is on the "auto" `power_dpm_force_performance_level` profile, and only that. All other options work. If you want to workaround the bug, you can use my service: https://github.com/illwieckz/dpm-query/ Just install the service (it will load "low/battery" DPM profile at startup), then use the `dpm-query` tool to set "high/performance" DPM profile when you need it. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/6f857c58/attachment.html>
[Bug 93706] Xorg freeze when running 3d app (Guild Wars 2) on RV620
https://bugs.freedesktop.org/show_bug.cgi?id=93706 --- Comment #13 from Michel Dänzer --- It's better to assume for now that the Guild Wars 2 and gsraytrace hangs are caused by different problems. Please keep the gsraytrace related discussion on the existing report(s) about that, in order not to clutter up this report. -- You are receiving this mail because: You are the assignee for the bug. -- next part -- An HTML attachment was scrubbed... URL: <http://lists.freedesktop.org/archives/dri-devel/attachments/20160115/cf32d332/attachment.html>
[PATCH v2 13/26] drm/fb_cma_helper: Remove implicit call to disable_unused_functions
Hi Maxime, Thank you for the patch. On Thursday 14 January 2016 16:24:56 Maxime Ripard wrote: > The drm_fbdev_cma_init function always calls the > drm_helper_disable_unused_functions. Since it's part of the usual probe > process, all the drivers using that helper will end up having their encoder > and CRTC disable functions called at probe if their device has not been > reported as enabled. > > This could be fixed by reading out from the registers the current state of > the device if it is enabled, but even that will not handle the case where > the device is actually disabled. > > Moreover, the drivers using the atomic modesetting expect that their enable > and disable callback to be called when the device is already enabled or > disabled (respectively). > > We can however fix this issue by moving the call to > drm_helper_disable_unused_functions out of drm_fbdev_cma_init and make the > drivers needing it (all the drivers calling drm_fbdev_cma_init and not > using the atomic modesetting) explicitly call it. I'd rather add it to all drivers that call drm_fbdev_cma_init(). All the atomic ones must have special code to cope with it that could be rendered useless by the removal of the drm_helper_disable_unused_functions() call. That code should be removed too, and it would be easier to check drivers one by one and fixing them individually (outside of this patch series, unless you insist ;-)) when removing the explicit drm_helper_disable_unused_functions() call. Other than that the patch looks fine to me. > Signed-off-by: Maxime Ripard > --- > drivers/gpu/drm/drm_fb_cma_helper.c | 3 --- > drivers/gpu/drm/imx/imx-drm-core.c | 1 + > drivers/gpu/drm/sti/sti_drv.c | 1 + > drivers/gpu/drm/tilcdc/tilcdc_drv.c | 1 + > 4 files changed, 3 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/drm_fb_cma_helper.c > b/drivers/gpu/drm/drm_fb_cma_helper.c index c19a62561183..daa98d881142 > 100644 > --- a/drivers/gpu/drm/drm_fb_cma_helper.c > +++ b/drivers/gpu/drm/drm_fb_cma_helper.c > @@ -348,9 +348,6 @@ struct drm_fbdev_cma *drm_fbdev_cma_init(struct > drm_device *dev, > > } > > - /* disable all the possible outputs/crtcs before entering KMS mode */ > - drm_helper_disable_unused_functions(dev); > - > ret = drm_fb_helper_initial_config(helper, preferred_bpp); > if (ret < 0) { > dev_err(dev->dev, "Failed to set initial hw configuration.\n"); > diff --git a/drivers/gpu/drm/imx/imx-drm-core.c > b/drivers/gpu/drm/imx/imx-drm-core.c index 7b990b4e96d2..e1db57791fc9 > 100644 > --- a/drivers/gpu/drm/imx/imx-drm-core.c > +++ b/drivers/gpu/drm/imx/imx-drm-core.c > @@ -312,6 +312,7 @@ static int imx_drm_driver_load(struct drm_device *drm, > unsigned long flags) dev_warn(drm->dev, "Invalid legacyfb_depth. > Defaulting to 16bpp\n"); legacyfb_depth = 16; > } > + drm_helper_disable_unused_functions(drm); > imxdrm->fbhelper = drm_fbdev_cma_init(drm, legacyfb_depth, > drm->mode_config.num_crtc, MAX_CRTC); > if (IS_ERR(imxdrm->fbhelper)) { > diff --git a/drivers/gpu/drm/sti/sti_drv.c b/drivers/gpu/drm/sti/sti_drv.c > index 1469987949d8..506b5626f3ed 100644 > --- a/drivers/gpu/drm/sti/sti_drv.c > +++ b/drivers/gpu/drm/sti/sti_drv.c > @@ -160,6 +160,7 @@ static int sti_load(struct drm_device *dev, unsigned > long flags) > > drm_mode_config_reset(dev); > > + drm_helper_disable_unused_functions(dev); > drm_fbdev_cma_init(dev, 32, > dev->mode_config.num_crtc, > dev->mode_config.num_connector); > diff --git a/drivers/gpu/drm/tilcdc/tilcdc_drv.c > b/drivers/gpu/drm/tilcdc/tilcdc_drv.c index 876cad58b1f9..24be31d69701 > 100644 > --- a/drivers/gpu/drm/tilcdc/tilcdc_drv.c > +++ b/drivers/gpu/drm/tilcdc/tilcdc_drv.c > @@ -294,6 +294,7 @@ static int tilcdc_load(struct drm_device *dev, unsigned > long flags) break; > } > > + drm_helper_disable_unused_functions(dev); > priv->fbdev = drm_fbdev_cma_init(dev, bpp, > dev->mode_config.num_crtc, > dev->mode_config.num_connector); -- Regards, Laurent Pinchart