Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1caeb408 authored by Murali Nalajala's avatar Murali Nalajala Committed by Greg Kroah-Hartman
Browse files

UPSTREAM: base: soc: Handle custom soc information sysfs entries



Soc framework exposed sysfs entries are not sufficient for some
of the h/w platforms. Currently there is no interface where soc
drivers can expose further information about their SoCs via soc
framework. This change address this limitation where clients can
pass their custom entries as attribute group and soc framework
would expose them as sysfs properties.

Bug: 141190076
Signed-off-by: default avatarMurali Nalajala <mnalajal@codeaurora.org>
Reviewed-by: default avatarBjorn Andersson <bjorn.andersson@linaro.org>
Reviewed-by: default avatarStephen Boyd <swboyd@chromium.org>
Link: https://lore.kernel.org/r/1570480662-25252-1-git-send-email-mnalajal@codeaurora.org


Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
(cherry-picked from c31e73121f4c1ec45a3e523ac6ce3ce6dafdcec1)
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@google.com>
Change-Id: Ia1c8d697e29052b4503da7c4b30c2c97d3b697f7
parent 630839ac
Loading
Loading
Loading
Loading
+17 −13
Original line number Original line Diff line number Diff line
@@ -104,15 +104,12 @@ static const struct attribute_group soc_attr_group = {
	.is_visible = soc_attribute_mode,
	.is_visible = soc_attribute_mode,
};
};


static const struct attribute_group *soc_attr_groups[] = {
	&soc_attr_group,
	NULL,
};

static void soc_release(struct device *dev)
static void soc_release(struct device *dev)
{
{
	struct soc_device *soc_dev = container_of(dev, struct soc_device, dev);
	struct soc_device *soc_dev = container_of(dev, struct soc_device, dev);


	ida_simple_remove(&soc_ida, soc_dev->soc_dev_num);
	kfree(soc_dev->dev.groups);
	kfree(soc_dev);
	kfree(soc_dev);
}
}


@@ -121,6 +118,7 @@ static struct soc_device_attribute *early_soc_dev_attr;
struct soc_device *soc_device_register(struct soc_device_attribute *soc_dev_attr)
struct soc_device *soc_device_register(struct soc_device_attribute *soc_dev_attr)
{
{
	struct soc_device *soc_dev;
	struct soc_device *soc_dev;
	const struct attribute_group **soc_attr_groups;
	int ret;
	int ret;


	if (!soc_bus_type.p) {
	if (!soc_bus_type.p) {
@@ -136,10 +134,18 @@ struct soc_device *soc_device_register(struct soc_device_attribute *soc_dev_attr
		goto out1;
		goto out1;
	}
	}


	soc_attr_groups = kcalloc(3, sizeof(*soc_attr_groups), GFP_KERNEL);
	if (!soc_attr_groups) {
		ret = -ENOMEM;
		goto out2;
	}
	soc_attr_groups[0] = &soc_attr_group;
	soc_attr_groups[1] = soc_dev_attr->custom_attr_group;

	/* Fetch a unique (reclaimable) SOC ID. */
	/* Fetch a unique (reclaimable) SOC ID. */
	ret = ida_simple_get(&soc_ida, 0, 0, GFP_KERNEL);
	ret = ida_simple_get(&soc_ida, 0, 0, GFP_KERNEL);
	if (ret < 0)
	if (ret < 0)
		goto out2;
		goto out3;
	soc_dev->soc_dev_num = ret;
	soc_dev->soc_dev_num = ret;


	soc_dev->attr = soc_dev_attr;
	soc_dev->attr = soc_dev_attr;
@@ -150,15 +156,15 @@ struct soc_device *soc_device_register(struct soc_device_attribute *soc_dev_attr
	dev_set_name(&soc_dev->dev, "soc%d", soc_dev->soc_dev_num);
	dev_set_name(&soc_dev->dev, "soc%d", soc_dev->soc_dev_num);


	ret = device_register(&soc_dev->dev);
	ret = device_register(&soc_dev->dev);
	if (ret)
	if (ret) {
		goto out3;
		put_device(&soc_dev->dev);
		return ERR_PTR(ret);
	}


	return soc_dev;
	return soc_dev;


out3:
out3:
	ida_simple_remove(&soc_ida, soc_dev->soc_dev_num);
	kfree(soc_attr_groups);
	put_device(&soc_dev->dev);
	soc_dev = NULL;
out2:
out2:
	kfree(soc_dev);
	kfree(soc_dev);
out1:
out1:
@@ -169,8 +175,6 @@ EXPORT_SYMBOL_GPL(soc_device_register);
/* Ensure soc_dev->attr is freed prior to calling soc_device_unregister. */
/* Ensure soc_dev->attr is freed prior to calling soc_device_unregister. */
void soc_device_unregister(struct soc_device *soc_dev)
void soc_device_unregister(struct soc_device *soc_dev)
{
{
	ida_simple_remove(&soc_ida, soc_dev->soc_dev_num);

	device_unregister(&soc_dev->dev);
	device_unregister(&soc_dev->dev);
	early_soc_dev_attr = NULL;
	early_soc_dev_attr = NULL;
}
}
+1 −0
Original line number Original line Diff line number Diff line
@@ -15,6 +15,7 @@ struct soc_device_attribute {
	const char *serial_number;
	const char *serial_number;
	const char *soc_id;
	const char *soc_id;
	const void *data;
	const void *data;
	const struct attribute_group *custom_attr_group;
};
};


/**
/**