static int img_ascii_lcd_probe()

in img-ascii-lcd.c [226:274]


static int img_ascii_lcd_probe(struct platform_device *pdev)
{
	const struct of_device_id *match;
	const struct img_ascii_lcd_config *cfg;
	struct device *dev = &pdev->dev;
	struct img_ascii_lcd_ctx *ctx;
	int err;

	match = of_match_device(img_ascii_lcd_matches, dev);
	if (!match)
		return -ENODEV;

	cfg = match->data;
	ctx = devm_kzalloc(dev, sizeof(*ctx) + cfg->num_chars, GFP_KERNEL);
	if (!ctx)
		return -ENOMEM;

	if (cfg->external_regmap) {
		ctx->regmap = syscon_node_to_regmap(dev->parent->of_node);
		if (IS_ERR(ctx->regmap))
			return PTR_ERR(ctx->regmap);

		if (of_property_read_u32(dev->of_node, "offset", &ctx->offset))
			return -EINVAL;
	} else {
		ctx->base = devm_platform_ioremap_resource(pdev, 0);
		if (IS_ERR(ctx->base))
			return PTR_ERR(ctx->base);
	}

	err = linedisp_register(&ctx->linedisp, dev, cfg->num_chars, ctx->curr,
				cfg->update);
	if (err)
		return err;

	/* for backwards compatibility */
	err = compat_only_sysfs_link_entry_to_kobj(&dev->kobj,
						   &ctx->linedisp.dev.kobj,
						   "message", NULL);
	if (err)
		goto err_unregister;

	platform_set_drvdata(pdev, ctx);
	return 0;

err_unregister:
	linedisp_unregister(&ctx->linedisp);
	return err;
}