Hi Paul.

On Tue, Jun 30, 2020 at 01:52:08AM +0200, Paul Cercueil wrote:
> All Ingenic SoCs starting from the JZ4725B support OSD mode.
> 
> In this mode, two separate planes can be used. They can have different
> positions and sizes, and one can be overlayed on top of the other.
> 
> Signed-off-by: Paul Cercueil <p...@crapouillou.net>

OSD? On screen Display?

Some random comments in the following - from my attempt to follow the
code.

        Sam


> ---
> 
> Notes:
>     v2: Use fallthrough; instead of /* fall-through */
> 
>  drivers/gpu/drm/ingenic/ingenic-drm-drv.c | 271 +++++++++++++++++-----
>  drivers/gpu/drm/ingenic/ingenic-drm.h     |  35 +++
>  2 files changed, 254 insertions(+), 52 deletions(-)
> 
> diff --git a/drivers/gpu/drm/ingenic/ingenic-drm-drv.c 
> b/drivers/gpu/drm/ingenic/ingenic-drm-drv.c
> index 6590b61cb915..a8573da1d577 100644
> --- a/drivers/gpu/drm/ingenic/ingenic-drm-drv.c
> +++ b/drivers/gpu/drm/ingenic/ingenic-drm-drv.c
> @@ -43,12 +43,13 @@ struct ingenic_dma_hwdesc {
>  
>  struct jz_soc_info {
>       bool needs_dev_clk;
> +     bool has_osd;
>       unsigned int max_width, max_height;
>  };
>  
>  struct ingenic_drm {
>       struct drm_device drm;
> -     struct drm_plane primary;
> +     struct drm_plane f0, f1;

A small comment about when f0 and f1 is used and how they are the
primary plane would be good here.


>       struct drm_crtc crtc;
>       struct drm_encoder encoder;
>  
> @@ -57,8 +58,8 @@ struct ingenic_drm {
>       struct clk *lcd_clk, *pix_clk;
>       const struct jz_soc_info *soc_info;
>  
> -     struct ingenic_dma_hwdesc *dma_hwdesc;
> -     dma_addr_t dma_hwdesc_phys;
> +     struct ingenic_dma_hwdesc *dma_hwdesc[2];
> +     dma_addr_t dma_hwdesc_phys[2];
>  
>       bool panel_is_sharp;
>  };
> @@ -90,7 +91,7 @@ static const struct regmap_config ingenic_drm_regmap_config 
> = {
>       .val_bits = 32,
>       .reg_stride = 4,
>  
> -     .max_register = JZ_REG_LCD_CMD1,
> +     .max_register = JZ_REG_LCD_SIZE1,
>       .writeable_reg = ingenic_drm_writeable_reg,
>  };
>  
> @@ -110,11 +111,6 @@ drm_encoder_get_priv(struct drm_encoder *encoder)
>       return container_of(encoder, struct ingenic_drm, encoder);
>  }
>  
> -static inline struct ingenic_drm *drm_plane_get_priv(struct drm_plane *plane)
> -{
> -     return container_of(plane, struct ingenic_drm, primary);
> -}
> -
>  static void ingenic_drm_crtc_atomic_enable(struct drm_crtc *crtc,
>                                          struct drm_crtc_state *state)
>  {
> @@ -185,34 +181,17 @@ static void ingenic_drm_crtc_update_timings(struct 
> ingenic_drm *priv,
>               regmap_write(priv->map, JZ_REG_LCD_SPL, hpe << 16 | (hpe + 1));
>               regmap_write(priv->map, JZ_REG_LCD_REV, mode->htotal << 16);
>       }
> -}
> -
> -static void ingenic_drm_crtc_update_ctrl(struct ingenic_drm *priv,
> -                                      const struct drm_format_info *finfo)
> -{
> -     unsigned int ctrl = JZ_LCD_CTRL_OFUP | JZ_LCD_CTRL_BURST_16;
> -
> -     switch (finfo->format) {
> -     case DRM_FORMAT_XRGB1555:
> -             ctrl |= JZ_LCD_CTRL_RGB555;
> -             /* fall-through */
> -     case DRM_FORMAT_RGB565:
> -             ctrl |= JZ_LCD_CTRL_BPP_15_16;
> -             break;
> -     case DRM_FORMAT_XRGB8888:
> -             ctrl |= JZ_LCD_CTRL_BPP_18_24;
> -             break;
> -     }
>  
>       regmap_update_bits(priv->map, JZ_REG_LCD_CTRL,
> -                        JZ_LCD_CTRL_OFUP | JZ_LCD_CTRL_BURST_16 |
> -                        JZ_LCD_CTRL_BPP_MASK, ctrl);
> +                        JZ_LCD_CTRL_OFUP | JZ_LCD_CTRL_BURST_16,
> +                        JZ_LCD_CTRL_OFUP | JZ_LCD_CTRL_BURST_16);
It looks like regmap_update_bits() is no longer the best choice here.

>  }
>  
>  static int ingenic_drm_crtc_atomic_check(struct drm_crtc *crtc,
>                                        struct drm_crtc_state *state)
>  {
>       struct ingenic_drm *priv = drm_crtc_get_priv(crtc);
> +     struct drm_plane_state *f1_state, *f0_state;
>       long rate;
>  
>       if (!drm_atomic_crtc_needs_modeset(state))
> @@ -227,6 +206,15 @@ static int ingenic_drm_crtc_atomic_check(struct drm_crtc 
> *crtc,
>       if (rate < 0)
>               return rate;
>  
> +     if (priv->soc_info->has_osd) {
> +             f1_state = drm_atomic_get_plane_state(state->state, &priv->f1);
> +             f0_state = drm_atomic_get_plane_state(state->state, &priv->f0);
> +
> +             /* If all the planes are disabled, we won't get a VBLANK IRQ */
> +             if (!f1_state->fb && !f0_state->fb)
> +                     state->no_vblank = true;
> +     }
> +
>       return 0;
>  }
>  
> @@ -236,14 +224,9 @@ static void ingenic_drm_crtc_atomic_flush(struct 
> drm_crtc *crtc,
>       struct ingenic_drm *priv = drm_crtc_get_priv(crtc);
>       struct drm_crtc_state *state = crtc->state;
>       struct drm_pending_vblank_event *event = state->event;
> -     struct drm_framebuffer *drm_fb = crtc->primary->state->fb;
> -     const struct drm_format_info *finfo;
>  
>       if (drm_atomic_crtc_needs_modeset(state)) {
> -             finfo = drm_format_info(drm_fb->format->format);
> -
>               ingenic_drm_crtc_update_timings(priv, &state->mode);
> -             ingenic_drm_crtc_update_ctrl(priv, finfo);
>  
>               clk_set_rate(priv->pix_clk, state->adjusted_mode.clock * 1000);
>       }
> @@ -260,12 +243,149 @@ static void ingenic_drm_crtc_atomic_flush(struct 
> drm_crtc *crtc,
>       }
>  }
>  
> +static int ingenic_drm_plane_atomic_check(struct drm_plane *plane,
> +                                       struct drm_plane_state *state)
> +{
> +     struct ingenic_drm *priv = drm_device_get_priv(plane->dev);
> +     struct drm_crtc_state *crtc_state;
> +     struct drm_crtc *crtc = state->crtc ?: plane->state->crtc;
> +     int ret;
> +
> +     if (!crtc)
> +             return 0;
> +
> +     crtc_state = drm_atomic_get_existing_crtc_state(state->state, crtc);
> +     if (WARN_ON(!crtc_state))
> +             return -EINVAL;
> +
> +     ret = drm_atomic_helper_check_plane_state(state, crtc_state,
> +                                               DRM_PLANE_HELPER_NO_SCALING,
> +                                               DRM_PLANE_HELPER_NO_SCALING,
> +                                               priv->soc_info->has_osd,
> +                                               true);
> +     if (ret)
> +             return ret;
> +
> +     if (!priv->soc_info->has_osd &&
> +         (state->src_x != 0 ||
> +          (state->src_w >> 16) != state->crtc_w ||
> +          (state->src_h >> 16) != state->crtc_h))
> +             return -EINVAL;
This check could bebefit from a small comment.
I cannot see the purpose of " >> 16" on the src_* fields...


> +
> +     /*
> +      * Require full modeset if if enabling or disabling a plane, or changing
Too many ifs?

> +      * its position, size or depth.
> +      */
> +     if (priv->soc_info->has_osd &&
> +         (!plane->state->fb || !state->fb ||
> +          plane->state->crtc_x != state->crtc_x ||
> +          plane->state->crtc_y != state->crtc_y ||
> +          plane->state->crtc_w != state->crtc_w ||
> +          plane->state->crtc_h != state->crtc_h ||
> +          plane->state->fb->format->format != state->fb->format->format))
> +             crtc_state->mode_changed = true;
> +
> +     return 0;
> +}
> +
> +static void ingenic_drm_plane_enable(struct ingenic_drm *priv,
> +                                   struct drm_plane *plane)
> +{
> +     unsigned int en_bit;
> +
> +     if (priv->soc_info->has_osd) {
> +             if (plane->type == DRM_PLANE_TYPE_PRIMARY)
> +                     en_bit = JZ_LCD_OSDC_F1EN;
> +             else
> +                     en_bit = JZ_LCD_OSDC_F0EN;
> +
> +             regmap_update_bits(priv->map, JZ_REG_LCD_OSDC, en_bit, en_bit);
I think you can use a more direct way to do the assignment.
Like before where the same pattern was used (last two arguments the
same).

> +     }
> +}
> +
> +static void ingenic_drm_plane_atomic_disable(struct drm_plane *plane,
> +                                          struct drm_plane_state *old_state)
> +{
> +     struct ingenic_drm *priv = drm_device_get_priv(plane->dev);
> +     unsigned int en_bit;
> +
> +     if (priv->soc_info->has_osd) {
> +             if (plane->type == DRM_PLANE_TYPE_PRIMARY)
> +                     en_bit = JZ_LCD_OSDC_F1EN;
> +             else
> +                     en_bit = JZ_LCD_OSDC_F0EN;
> +
> +             regmap_update_bits(priv->map, JZ_REG_LCD_OSDC, en_bit, 0);
> +     }
> +}
> +
> +static void ingenic_drm_plane_config(struct ingenic_drm *priv,
> +                                  struct drm_plane *plane, u32 fourcc)
> +{
> +     struct drm_plane_state *state = plane->state;
> +     unsigned int xy_reg, size_reg;
> +     unsigned int ctrl = 0;
> +
> +     ingenic_drm_plane_enable(priv, plane);
> +
> +     if (priv->soc_info->has_osd &&
> +         plane->type == DRM_PLANE_TYPE_PRIMARY) {
> +             switch (fourcc) {
> +             case DRM_FORMAT_XRGB1555:
> +                     ctrl |= JZ_LCD_OSDCTRL_RGB555;
> +                     fallthrough;
> +             case DRM_FORMAT_RGB565:
> +                     ctrl |= JZ_LCD_OSDCTRL_BPP_15_16;
> +                     break;
> +             case DRM_FORMAT_XRGB8888:
> +                     ctrl |= JZ_LCD_OSDCTRL_BPP_18_24;
> +                     break;
> +             }
> +
> +             regmap_update_bits(priv->map, JZ_REG_LCD_OSDCTRL,
> +                                JZ_LCD_OSDCTRL_BPP_MASK, ctrl);
> +     } else {
> +             switch (fourcc) {
> +             case DRM_FORMAT_XRGB1555:
> +                     ctrl |= JZ_LCD_CTRL_RGB555;
> +                     fallthrough;
> +             case DRM_FORMAT_RGB565:
> +                     ctrl |= JZ_LCD_CTRL_BPP_15_16;
> +                     break;
> +             case DRM_FORMAT_XRGB8888:
> +                     ctrl |= JZ_LCD_CTRL_BPP_18_24;
> +                     break;
> +             }
> +
> +             regmap_update_bits(priv->map, JZ_REG_LCD_CTRL,
> +                                JZ_LCD_CTRL_BPP_MASK, ctrl);
> +     }
> +
> +     if (priv->soc_info->has_osd) {
> +             if (plane->type == DRM_PLANE_TYPE_PRIMARY) {
> +                     xy_reg = JZ_REG_LCD_XYP1;
> +                     size_reg = JZ_REG_LCD_SIZE1;
> +             } else {
> +                     xy_reg = JZ_REG_LCD_XYP0;
> +                     size_reg = JZ_REG_LCD_SIZE0;
> +             }
> +
> +             regmap_write(priv->map, xy_reg,
> +                          state->crtc_x << JZ_LCD_XYP01_XPOS_LSB |
> +                          state->crtc_y << JZ_LCD_XYP01_YPOS_LSB);
> +             regmap_write(priv->map, size_reg,
> +                          state->crtc_w << JZ_LCD_SIZE01_WIDTH_LSB |
> +                          state->crtc_h << JZ_LCD_SIZE01_HEIGHT_LSB);
> +     }
> +}
> +
>  static void ingenic_drm_plane_atomic_update(struct drm_plane *plane,
>                                           struct drm_plane_state *oldstate)
>  {
> -     struct ingenic_drm *priv = drm_plane_get_priv(plane);
> +     struct ingenic_drm *priv = drm_device_get_priv(plane->dev);
>       struct drm_plane_state *state = plane->state;
>       unsigned int width, height, cpp;
> +     unsigned int hwdesc_idx;
>       dma_addr_t addr;
>  
>       if (state && state->fb) {
> @@ -274,9 +394,18 @@ static void ingenic_drm_plane_atomic_update(struct 
> drm_plane *plane,
>               height = state->src_h >> 16;
>               cpp = state->fb->format->cpp[0];
>  
> -             priv->dma_hwdesc->addr = addr;
> -             priv->dma_hwdesc->cmd = width * height * cpp / 4;
> -             priv->dma_hwdesc->cmd |= JZ_LCD_CMD_EOF_IRQ;
> +             if (!priv->soc_info->has_osd)
> +                     hwdesc_idx = 0;
> +             else

> +                     hwdesc_idx = plane->type == DRM_PLANE_TYPE_PRIMARY;
This looks ugly.
"plane->type == DRM_PLANE_TYPE_PRIMARY" evaluates to a boolean.
This is then ocnverted to an int used as index to an array later.
Something a bit more explicit would be more readable.


> +
> +             priv->dma_hwdesc[hwdesc_idx]->addr = addr;
> +             priv->dma_hwdesc[hwdesc_idx]->cmd = width * height * cpp / 4;
> +             priv->dma_hwdesc[hwdesc_idx]->cmd |= JZ_LCD_CMD_EOF_IRQ;
> +
> +             if (drm_atomic_crtc_needs_modeset(state->crtc->state))
> +                     ingenic_drm_plane_config(priv, plane,
> +                                              state->fb->format->format);
>       }
>  }
>  
> @@ -437,6 +566,8 @@ static const struct drm_crtc_funcs ingenic_drm_crtc_funcs 
> = {
>  
>  static const struct drm_plane_helper_funcs ingenic_drm_plane_helper_funcs = {
>       .atomic_update          = ingenic_drm_plane_atomic_update,
> +     .atomic_check           = ingenic_drm_plane_atomic_check,
> +     .atomic_disable         = ingenic_drm_plane_atomic_disable,
>       .prepare_fb             = drm_gem_fb_prepare_fb,
>  };
>  
> @@ -463,8 +594,10 @@ static void ingenic_drm_free_dma_hwdesc(void *d)
>  {
>       struct ingenic_drm *priv = d;
>  
> -     dma_free_coherent(priv->dev, sizeof(*priv->dma_hwdesc),
> -                       priv->dma_hwdesc, priv->dma_hwdesc_phys);
> +     dma_free_coherent(priv->dev, sizeof(*priv->dma_hwdesc[0]),
> +                       priv->dma_hwdesc[0], priv->dma_hwdesc_phys[0]);
> +     dma_free_coherent(priv->dev, sizeof(*priv->dma_hwdesc[1]),
> +                       priv->dma_hwdesc[1], priv->dma_hwdesc_phys[1]);
>  }
>  
>  static int ingenic_drm_probe(struct platform_device *pdev)
> @@ -549,23 +682,32 @@ static int ingenic_drm_probe(struct platform_device 
> *pdev)
>               bridge = devm_drm_panel_bridge_add_typed(dev, panel,
>                                                        
> DRM_MODE_CONNECTOR_DPI);
>  
> -     priv->dma_hwdesc = dma_alloc_coherent(dev, sizeof(*priv->dma_hwdesc),
> -                                           &priv->dma_hwdesc_phys,
> -                                           GFP_KERNEL);
> -     if (!priv->dma_hwdesc)
> +     priv->dma_hwdesc[0] = dma_alloc_coherent(dev, 
> sizeof(*priv->dma_hwdesc[0]),
> +                                              &priv->dma_hwdesc_phys[0],
> +                                              GFP_KERNEL);
> +     if (!priv->dma_hwdesc[0])
> +             return -ENOMEM;
> +
> +     priv->dma_hwdesc[0]->next = priv->dma_hwdesc_phys[0];
> +     priv->dma_hwdesc[0]->id = 0xdeafbead;
> +
> +     priv->dma_hwdesc[1] = dma_alloc_coherent(dev, 
> sizeof(*priv->dma_hwdesc[1]),
> +                                              &priv->dma_hwdesc_phys[1],
> +                                              GFP_KERNEL);
> +     if (!priv->dma_hwdesc[1])
>               return -ENOMEM;
Here you should undo the first allocation??
I think the code could benefit from using dmam_alloc_coherent().

>  
> +     priv->dma_hwdesc[1]->next = priv->dma_hwdesc_phys[1];
> +     priv->dma_hwdesc[1]->id = 0xdeadbabe;
> +
>       ret = devm_add_action_or_reset(dev, ingenic_drm_free_dma_hwdesc, priv);
>       if (ret)
>               return ret;
>  
> -     priv->dma_hwdesc->next = priv->dma_hwdesc_phys;
> -     priv->dma_hwdesc->id = 0xdeafbead;
> -
> -     drm_plane_helper_add(&priv->primary, &ingenic_drm_plane_helper_funcs);
> +     drm_plane_helper_add(&priv->f1, &ingenic_drm_plane_helper_funcs);
>  
> -     ret = drm_universal_plane_init(drm, &priv->primary,
> -                                    0, &ingenic_drm_primary_plane_funcs,
> +     ret = drm_universal_plane_init(drm, &priv->f1, 1,
> +                                    &ingenic_drm_primary_plane_funcs,
>                                      ingenic_drm_primary_formats,
>                                      ARRAY_SIZE(ingenic_drm_primary_formats),
>                                      NULL, DRM_PLANE_TYPE_PRIMARY, NULL);
> @@ -576,13 +718,30 @@ static int ingenic_drm_probe(struct platform_device 
> *pdev)
>  
>       drm_crtc_helper_add(&priv->crtc, &ingenic_drm_crtc_helper_funcs);
>  
> -     ret = drm_crtc_init_with_planes(drm, &priv->crtc, &priv->primary,
> +     ret = drm_crtc_init_with_planes(drm, &priv->crtc, &priv->f1,
>                                       NULL, &ingenic_drm_crtc_funcs, NULL);
>       if (ret) {
>               dev_err(dev, "Failed to init CRTC: %i\n", ret);
>               return ret;
>       }
>  
> +     if (soc_info->has_osd) {
> +             drm_plane_helper_add(&priv->f0,
> +                                  &ingenic_drm_plane_helper_funcs);
> +
> +             ret = drm_universal_plane_init(drm, &priv->f0, 1,
> +                                            &ingenic_drm_primary_plane_funcs,
> +                                            ingenic_drm_primary_formats,
> +                                            
> ARRAY_SIZE(ingenic_drm_primary_formats),
> +                                            NULL, DRM_PLANE_TYPE_OVERLAY,
> +                                            NULL);
> +             if (ret) {
> +                     dev_err(dev, "Failed to register overlay plane: %i\n",
> +                             ret);
> +                     return ret;
> +             }
> +     }
> +
>       priv->encoder.possible_crtcs = 1;
>  
>       drm_encoder_helper_add(&priv->encoder,
> @@ -644,7 +803,12 @@ static int ingenic_drm_probe(struct platform_device 
> *pdev)
>       }
>  
>       /* Set address of our DMA descriptor chain */
> -     regmap_write(priv->map, JZ_REG_LCD_DA0, priv->dma_hwdesc_phys);
> +     regmap_write(priv->map, JZ_REG_LCD_DA0, priv->dma_hwdesc_phys[0]);
> +     regmap_write(priv->map, JZ_REG_LCD_DA1, priv->dma_hwdesc_phys[1]);
> +
> +     /* Enable OSD if available */
> +     if (soc_info->has_osd)
> +             regmap_write(priv->map, JZ_REG_LCD_OSDC, JZ_LCD_OSDC_OSDEN);
>  
>       ret = drm_dev_register(drm, 0);
>       if (ret) {
> @@ -680,18 +844,21 @@ static int ingenic_drm_remove(struct platform_device 
> *pdev)
>  
>  static const struct jz_soc_info jz4740_soc_info = {
>       .needs_dev_clk = true,
> +     .has_osd = false,
>       .max_width = 800,
>       .max_height = 600,
>  };
>  
>  static const struct jz_soc_info jz4725b_soc_info = {
>       .needs_dev_clk = false,
> +     .has_osd = true,
>       .max_width = 800,
>       .max_height = 600,
>  };
>  
>  static const struct jz_soc_info jz4770_soc_info = {
>       .needs_dev_clk = false,
> +     .has_osd = true,
>       .max_width = 1280,
>       .max_height = 720,
>  };
> diff --git a/drivers/gpu/drm/ingenic/ingenic-drm.h 
> b/drivers/gpu/drm/ingenic/ingenic-drm.h
> index cb578cff7bb1..d0b827a9fe83 100644
> --- a/drivers/gpu/drm/ingenic/ingenic-drm.h
> +++ b/drivers/gpu/drm/ingenic/ingenic-drm.h
> @@ -30,6 +30,18 @@
>  #define JZ_REG_LCD_SA1                               0x54
>  #define JZ_REG_LCD_FID1                              0x58
>  #define JZ_REG_LCD_CMD1                              0x5C
> +#define JZ_REG_LCD_OSDC                              0x100
> +#define JZ_REG_LCD_OSDCTRL                   0x104
> +#define JZ_REG_LCD_OSDS                              0x108
> +#define JZ_REG_LCD_BGC                               0x10c
> +#define JZ_REG_LCD_KEY0                              0x110
> +#define JZ_REG_LCD_KEY1                              0x114
> +#define JZ_REG_LCD_ALPHA                     0x118
> +#define JZ_REG_LCD_IPUR                              0x11c
> +#define JZ_REG_LCD_XYP0                              0x120
> +#define JZ_REG_LCD_XYP1                              0x124
> +#define JZ_REG_LCD_SIZE0                     0x128
> +#define JZ_REG_LCD_SIZE1                     0x12c
>  
>  #define JZ_LCD_CFG_SLCD                              BIT(31)
>  #define JZ_LCD_CFG_PS_DISABLE                        BIT(23)
> @@ -123,4 +135,27 @@
>  #define JZ_LCD_STATE_SOF_IRQ                 BIT(4)
>  #define JZ_LCD_STATE_DISABLED                        BIT(0)
>  
> +#define JZ_LCD_OSDC_OSDEN                    BIT(0)
> +#define JZ_LCD_OSDC_F0EN                     BIT(3)
> +#define JZ_LCD_OSDC_F1EN                     BIT(4)
> +
> +#define JZ_LCD_OSDCTRL_IPU                   BIT(15)
> +#define JZ_LCD_OSDCTRL_RGB555                        BIT(4)
> +#define JZ_LCD_OSDCTRL_CHANGE                        BIT(3)
> +#define JZ_LCD_OSDCTRL_BPP_15_16             0x4
> +#define JZ_LCD_OSDCTRL_BPP_18_24             0x5
> +#define JZ_LCD_OSDCTRL_BPP_30                        0x7
> +#define JZ_LCD_OSDCTRL_BPP_MASK                      (JZ_LCD_OSDCTRL_RGB555 
> | 0x7)
> +
> +#define JZ_LCD_OSDS_READY                    BIT(0)
> +
> +#define JZ_LCD_IPUR_IPUREN                   BIT(31)
> +#define JZ_LCD_IPUR_IPUR_LSB                 0
> +
> +#define JZ_LCD_XYP01_XPOS_LSB                        0
> +#define JZ_LCD_XYP01_YPOS_LSB                        16
> +
> +#define JZ_LCD_SIZE01_WIDTH_LSB                      0
> +#define JZ_LCD_SIZE01_HEIGHT_LSB             16
> +
>  #endif /* DRIVERS_GPU_DRM_INGENIC_INGENIC_DRM_H */
> -- 
> 2.27.0
> 
> _______________________________________________
> dri-devel mailing list
> dri-devel@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/dri-devel
_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

Reply via email to