auxdisplay: linedisp: Allocate buffer for the string
authorAndy Shevchenko <andriy.shevchenko@linux.intel.com>
Mon, 19 Feb 2024 16:58:01 +0000 (18:58 +0200)
committerAndy Shevchenko <andriy.shevchenko@linux.intel.com>
Mon, 26 Feb 2024 16:02:19 +0000 (18:02 +0200)
Always allocate a buffer for the currently displayed characters.
It makes the line display API simpler.

Reviewed-by: Geert Uytterhoeven <geert@linux-m68k.org>
Tested-by: Geert Uytterhoeven <geert@linux-m68k.org>
Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
drivers/auxdisplay/ht16k33.c
drivers/auxdisplay/img-ascii-lcd.c
drivers/auxdisplay/line-display.c
drivers/auxdisplay/line-display.h

index 32d3afd29177aaef85fd105a8b32eda288ffaf15..19805f39a25735851c1e9ca9cbda35bf46e6fd48 100644 (file)
@@ -92,7 +92,6 @@ struct ht16k33_seg {
                struct seg14_conversion_map seg14;
        } map;
        unsigned int map_size;
-       char curr[4];
 };
 
 struct ht16k33_priv {
@@ -457,7 +456,7 @@ static void ht16k33_seg7_update(struct work_struct *work)
        struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
                                                 work.work);
        struct ht16k33_seg *seg = &priv->seg;
-       char *s = seg->curr;
+       char *s = seg->linedisp.buf;
        uint8_t buf[9];
 
        buf[0] = map_to_seg7(&seg->map.seg7, *s++);
@@ -478,7 +477,7 @@ static void ht16k33_seg14_update(struct work_struct *work)
        struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
                                                 work.work);
        struct ht16k33_seg *seg = &priv->seg;
-       char *s = seg->curr;
+       char *s = seg->linedisp.buf;
        uint8_t buf[8];
 
        put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf);
@@ -700,8 +699,7 @@ static int ht16k33_seg_probe(struct device *dev, struct ht16k33_priv *priv,
        if (err)
                return err;
 
-       err = linedisp_register(&seg->linedisp, dev, 4, seg->curr,
-                               &ht16k33_linedisp_ops);
+       err = linedisp_register(&seg->linedisp, dev, 4, &ht16k33_linedisp_ops);
        if (err)
                goto err_remove_map_file;
 
index ecfb1c05bf557ad52cf700f360d78f4f854ff743..925c4cd101e98314a2bf2d490a8caa76bfe77526 100644 (file)
@@ -37,7 +37,6 @@ struct img_ascii_lcd_config {
  * @regmap: the regmap through which LCD registers are accessed
  * @offset: the offset within regmap to the start of the LCD registers
  * @cfg: pointer to the LCD model configuration
- * @curr: the string currently displayed on the LCD
  */
 struct img_ascii_lcd_ctx {
        struct linedisp linedisp;
@@ -47,7 +46,6 @@ struct img_ascii_lcd_ctx {
        };
        u32 offset;
        const struct img_ascii_lcd_config *cfg;
-       char curr[] __aligned(8);
 };
 
 /*
@@ -61,12 +59,12 @@ static void boston_update(struct linedisp *linedisp)
        ulong val;
 
 #if BITS_PER_LONG == 64
-       val = *((u64 *)&ctx->curr[0]);
+       val = *((u64 *)&linedisp->buf[0]);
        __raw_writeq(val, ctx->base);
 #elif BITS_PER_LONG == 32
-       val = *((u32 *)&ctx->curr[0]);
+       val = *((u32 *)&linedisp->buf[0]);
        __raw_writel(val, ctx->base);
-       val = *((u32 *)&ctx->curr[4]);
+       val = *((u32 *)&linedisp->buf[4]);
        __raw_writel(val, ctx->base + 4);
 #else
 # error Not 32 or 64 bit
@@ -93,7 +91,7 @@ static void malta_update(struct linedisp *linedisp)
 
        for (i = 0; i < linedisp->num_chars; i++) {
                err = regmap_write(ctx->regmap,
-                                  ctx->offset + (i * 8), ctx->curr[i]);
+                                  ctx->offset + (i * 8), linedisp->buf[i]);
                if (err)
                        break;
        }
@@ -195,7 +193,7 @@ static void sead3_update(struct linedisp *linedisp)
 
                err = regmap_write(ctx->regmap,
                                   ctx->offset + SEAD3_REG_LCD_DATA,
-                                  ctx->curr[i]);
+                                  linedisp->buf[i]);
                if (err)
                        break;
        }
@@ -236,7 +234,7 @@ static int img_ascii_lcd_probe(struct platform_device *pdev)
        struct img_ascii_lcd_ctx *ctx;
        int err;
 
-       ctx = devm_kzalloc(dev, sizeof(*ctx) + cfg->num_chars, GFP_KERNEL);
+       ctx = devm_kzalloc(dev, sizeof(*ctx), GFP_KERNEL);
        if (!ctx)
                return -ENOMEM;
 
@@ -253,8 +251,7 @@ static int img_ascii_lcd_probe(struct platform_device *pdev)
                        return PTR_ERR(ctx->base);
        }
 
-       err = linedisp_register(&ctx->linedisp, dev, cfg->num_chars, ctx->curr,
-                               &cfg->ops);
+       err = linedisp_register(&ctx->linedisp, dev, cfg->num_chars, &cfg->ops);
        if (err)
                return err;
 
index 13be7c2f6bc362d1655f1dcb88f2358218886d93..e2b546210f8d8d6d20199044699147f307577a2c 100644 (file)
@@ -265,6 +265,7 @@ static void linedisp_release(struct device *dev)
 
        kfree(linedisp->map);
        kfree(linedisp->message);
+       kfree(linedisp->buf);
        ida_free(&linedisp_id, linedisp->id);
 }
 
@@ -316,14 +317,12 @@ static int linedisp_init_map(struct linedisp *linedisp)
  * @linedisp: pointer to character line display structure
  * @parent: parent device
  * @num_chars: the number of characters that can be displayed
- * @buf: pointer to a buffer that can hold @num_chars characters
  * @ops: character line display operations
  *
  * Return: zero on success, else a negative error code.
  */
 int linedisp_register(struct linedisp *linedisp, struct device *parent,
-                     unsigned int num_chars, char *buf,
-                     const struct linedisp_ops *ops)
+                     unsigned int num_chars, const struct linedisp_ops *ops)
 {
        int err;
 
@@ -331,7 +330,6 @@ int linedisp_register(struct linedisp *linedisp, struct device *parent,
        linedisp->dev.parent = parent;
        linedisp->dev.type = &linedisp_type;
        linedisp->ops = ops;
-       linedisp->buf = buf;
        linedisp->num_chars = num_chars;
        linedisp->scroll_rate = DEFAULT_SCROLL_RATE;
 
@@ -343,6 +341,11 @@ int linedisp_register(struct linedisp *linedisp, struct device *parent,
        device_initialize(&linedisp->dev);
        dev_set_name(&linedisp->dev, "linedisp.%u", linedisp->id);
 
+       err = -ENOMEM;
+       linedisp->buf = kzalloc(linedisp->num_chars, GFP_KERNEL);
+       if (!linedisp->buf)
+               goto out_put_device;
+
        /* initialise a character mapping, if required */
        err = linedisp_init_map(linedisp);
        if (err)
index 4e310b0e611efde81f29a7185205a5266148970e..4348d7a2f69ade792cb059cf21540d39d6c3f749 100644 (file)
@@ -82,8 +82,7 @@ struct linedisp {
 };
 
 int linedisp_register(struct linedisp *linedisp, struct device *parent,
-                     unsigned int num_chars, char *buf,
-                     const struct linedisp_ops *ops);
+                     unsigned int num_chars, const struct linedisp_ops *ops);
 void linedisp_unregister(struct linedisp *linedisp);
 
 #endif /* LINEDISP_H */