mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-11 04:18:39 +08:00
auxdisplay: linedisp: Allocate buffer for the string
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>
This commit is contained in:
parent
34ddc83dc7
commit
4ce026d5f4
@ -92,7 +92,6 @@ struct ht16k33_seg {
|
|||||||
struct seg14_conversion_map seg14;
|
struct seg14_conversion_map seg14;
|
||||||
} map;
|
} map;
|
||||||
unsigned int map_size;
|
unsigned int map_size;
|
||||||
char curr[4];
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct ht16k33_priv {
|
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,
|
struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
|
||||||
work.work);
|
work.work);
|
||||||
struct ht16k33_seg *seg = &priv->seg;
|
struct ht16k33_seg *seg = &priv->seg;
|
||||||
char *s = seg->curr;
|
char *s = seg->linedisp.buf;
|
||||||
uint8_t buf[9];
|
uint8_t buf[9];
|
||||||
|
|
||||||
buf[0] = map_to_seg7(&seg->map.seg7, *s++);
|
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,
|
struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
|
||||||
work.work);
|
work.work);
|
||||||
struct ht16k33_seg *seg = &priv->seg;
|
struct ht16k33_seg *seg = &priv->seg;
|
||||||
char *s = seg->curr;
|
char *s = seg->linedisp.buf;
|
||||||
uint8_t buf[8];
|
uint8_t buf[8];
|
||||||
|
|
||||||
put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf);
|
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)
|
if (err)
|
||||||
return err;
|
return err;
|
||||||
|
|
||||||
err = linedisp_register(&seg->linedisp, dev, 4, seg->curr,
|
err = linedisp_register(&seg->linedisp, dev, 4, &ht16k33_linedisp_ops);
|
||||||
&ht16k33_linedisp_ops);
|
|
||||||
if (err)
|
if (err)
|
||||||
goto err_remove_map_file;
|
goto err_remove_map_file;
|
||||||
|
|
||||||
|
@ -37,7 +37,6 @@ struct img_ascii_lcd_config {
|
|||||||
* @regmap: the regmap through which LCD registers are accessed
|
* @regmap: the regmap through which LCD registers are accessed
|
||||||
* @offset: the offset within regmap to the start of the LCD registers
|
* @offset: the offset within regmap to the start of the LCD registers
|
||||||
* @cfg: pointer to the LCD model configuration
|
* @cfg: pointer to the LCD model configuration
|
||||||
* @curr: the string currently displayed on the LCD
|
|
||||||
*/
|
*/
|
||||||
struct img_ascii_lcd_ctx {
|
struct img_ascii_lcd_ctx {
|
||||||
struct linedisp linedisp;
|
struct linedisp linedisp;
|
||||||
@ -47,7 +46,6 @@ struct img_ascii_lcd_ctx {
|
|||||||
};
|
};
|
||||||
u32 offset;
|
u32 offset;
|
||||||
const struct img_ascii_lcd_config *cfg;
|
const struct img_ascii_lcd_config *cfg;
|
||||||
char curr[] __aligned(8);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -61,12 +59,12 @@ static void boston_update(struct linedisp *linedisp)
|
|||||||
ulong val;
|
ulong val;
|
||||||
|
|
||||||
#if BITS_PER_LONG == 64
|
#if BITS_PER_LONG == 64
|
||||||
val = *((u64 *)&ctx->curr[0]);
|
val = *((u64 *)&linedisp->buf[0]);
|
||||||
__raw_writeq(val, ctx->base);
|
__raw_writeq(val, ctx->base);
|
||||||
#elif BITS_PER_LONG == 32
|
#elif BITS_PER_LONG == 32
|
||||||
val = *((u32 *)&ctx->curr[0]);
|
val = *((u32 *)&linedisp->buf[0]);
|
||||||
__raw_writel(val, ctx->base);
|
__raw_writel(val, ctx->base);
|
||||||
val = *((u32 *)&ctx->curr[4]);
|
val = *((u32 *)&linedisp->buf[4]);
|
||||||
__raw_writel(val, ctx->base + 4);
|
__raw_writel(val, ctx->base + 4);
|
||||||
#else
|
#else
|
||||||
# error Not 32 or 64 bit
|
# 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++) {
|
for (i = 0; i < linedisp->num_chars; i++) {
|
||||||
err = regmap_write(ctx->regmap,
|
err = regmap_write(ctx->regmap,
|
||||||
ctx->offset + (i * 8), ctx->curr[i]);
|
ctx->offset + (i * 8), linedisp->buf[i]);
|
||||||
if (err)
|
if (err)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -195,7 +193,7 @@ static void sead3_update(struct linedisp *linedisp)
|
|||||||
|
|
||||||
err = regmap_write(ctx->regmap,
|
err = regmap_write(ctx->regmap,
|
||||||
ctx->offset + SEAD3_REG_LCD_DATA,
|
ctx->offset + SEAD3_REG_LCD_DATA,
|
||||||
ctx->curr[i]);
|
linedisp->buf[i]);
|
||||||
if (err)
|
if (err)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -236,7 +234,7 @@ static int img_ascii_lcd_probe(struct platform_device *pdev)
|
|||||||
struct img_ascii_lcd_ctx *ctx;
|
struct img_ascii_lcd_ctx *ctx;
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
ctx = devm_kzalloc(dev, sizeof(*ctx) + cfg->num_chars, GFP_KERNEL);
|
ctx = devm_kzalloc(dev, sizeof(*ctx), GFP_KERNEL);
|
||||||
if (!ctx)
|
if (!ctx)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
@ -253,8 +251,7 @@ static int img_ascii_lcd_probe(struct platform_device *pdev)
|
|||||||
return PTR_ERR(ctx->base);
|
return PTR_ERR(ctx->base);
|
||||||
}
|
}
|
||||||
|
|
||||||
err = linedisp_register(&ctx->linedisp, dev, cfg->num_chars, ctx->curr,
|
err = linedisp_register(&ctx->linedisp, dev, cfg->num_chars, &cfg->ops);
|
||||||
&cfg->ops);
|
|
||||||
if (err)
|
if (err)
|
||||||
return err;
|
return err;
|
||||||
|
|
||||||
|
@ -265,6 +265,7 @@ static void linedisp_release(struct device *dev)
|
|||||||
|
|
||||||
kfree(linedisp->map);
|
kfree(linedisp->map);
|
||||||
kfree(linedisp->message);
|
kfree(linedisp->message);
|
||||||
|
kfree(linedisp->buf);
|
||||||
ida_free(&linedisp_id, linedisp->id);
|
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
|
* @linedisp: pointer to character line display structure
|
||||||
* @parent: parent device
|
* @parent: parent device
|
||||||
* @num_chars: the number of characters that can be displayed
|
* @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
|
* @ops: character line display operations
|
||||||
*
|
*
|
||||||
* Return: zero on success, else a negative error code.
|
* Return: zero on success, else a negative error code.
|
||||||
*/
|
*/
|
||||||
int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
||||||
unsigned int num_chars, char *buf,
|
unsigned int num_chars, const struct linedisp_ops *ops)
|
||||||
const struct linedisp_ops *ops)
|
|
||||||
{
|
{
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
@ -331,7 +330,6 @@ int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
|||||||
linedisp->dev.parent = parent;
|
linedisp->dev.parent = parent;
|
||||||
linedisp->dev.type = &linedisp_type;
|
linedisp->dev.type = &linedisp_type;
|
||||||
linedisp->ops = ops;
|
linedisp->ops = ops;
|
||||||
linedisp->buf = buf;
|
|
||||||
linedisp->num_chars = num_chars;
|
linedisp->num_chars = num_chars;
|
||||||
linedisp->scroll_rate = DEFAULT_SCROLL_RATE;
|
linedisp->scroll_rate = DEFAULT_SCROLL_RATE;
|
||||||
|
|
||||||
@ -343,6 +341,11 @@ int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
|||||||
device_initialize(&linedisp->dev);
|
device_initialize(&linedisp->dev);
|
||||||
dev_set_name(&linedisp->dev, "linedisp.%u", linedisp->id);
|
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 */
|
/* initialise a character mapping, if required */
|
||||||
err = linedisp_init_map(linedisp);
|
err = linedisp_init_map(linedisp);
|
||||||
if (err)
|
if (err)
|
||||||
|
@ -82,8 +82,7 @@ struct linedisp {
|
|||||||
};
|
};
|
||||||
|
|
||||||
int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
int linedisp_register(struct linedisp *linedisp, struct device *parent,
|
||||||
unsigned int num_chars, char *buf,
|
unsigned int num_chars, const struct linedisp_ops *ops);
|
||||||
const struct linedisp_ops *ops);
|
|
||||||
void linedisp_unregister(struct linedisp *linedisp);
|
void linedisp_unregister(struct linedisp *linedisp);
|
||||||
|
|
||||||
#endif /* LINEDISP_H */
|
#endif /* LINEDISP_H */
|
||||||
|
Loading…
Reference in New Issue
Block a user