* [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-19 14:38 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-19 14:26 UTC (permalink / raw) To: linuxppc-dev, linux, jdelvare, lm-sensors; +Cc: sbhat This patch adds basic kernel enablement for reading power values, fan speed rpm and temperature values on powernv platforms which will be exported to user space through sysfs interface. Test results: ------------- [root@tul163p1 ~]# sensors ibmpowernv-isa-0000 Adapter: ISA adapter fan1: 5487 RPM (min = 0 RPM) fan2: 5152 RPM (min = 0 RPM) fan3: 5590 RPM (min = 0 RPM) fan4: 4963 RPM (min = 0 RPM) fan5: 0 RPM (min = 0 RPM) fan6: 0 RPM (min = 0 RPM) fan7: 7488 RPM (min = 0 RPM) fan8: 7944 RPM (min = 0 RPM) temp1: +39.0°C (high = +0.0°C) power1: 192.00 W [root@tul163p1 ~]# ls /sys/devices/platform/ alarmtimer ibmpowernv.0 rtc-generic serial8250 uevent [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/ driver/ hwmon/ modalias subsystem/ uevent [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/hwmon/hwmon0/ device fan2_min fan4_min fan6_min fan8_min power1_input fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent fan2_input fan4_input fan6_input fan8_input name [root@tul163p1 ~]# [root@tul163p1 ~]# ls /sys/class/hwmon/hwmon0/ device fan2_min fan4_min fan6_min fan8_min power1_input fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent fan2_input fan4_input fan6_input fan8_input name [root@tul163p1 ~]# Signed-off-by: Neelesh Gupta <neelegup@linux.vnet.ibm.com> --- Changes in v2 ============= - Generic use of devm_* functions in hwmon like using devm_kzalloc() for dynamic memory request, avoiding the need to explicit free of memory. Adding 'struct attribute_group' as member of platform data structure to be populated and then passed to devm_hwmon_device_register_with_groups(). Note: Having an array of pointers of 'attribute_group' and each group corresponds to 'enum sensors' type. Not completely sure, if it's ideal or could have just one group populated with attributes of sensor types? - 'ibmpowernv' is not hot-pluggable device so moving 'platform_driver' callback function (probe) as part of __init code. - Fixed issues related to coding style. - Other general comments in v1. drivers/hwmon/Kconfig | 8 + drivers/hwmon/Makefile | 1 drivers/hwmon/ibmpowernv.c | 368 ++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 377 insertions(+) create mode 100644 drivers/hwmon/ibmpowernv.c diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index bc196f4..3e308fa 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig @@ -554,6 +554,14 @@ config SENSORS_IBMPEX This driver can also be built as a module. If so, the module will be called ibmpex. +config SENSORS_IBMPOWERNV + tristate "IBM POWERNV platform sensors" + depends on PPC_POWERNV + default y + help + If you say yes here you get support for the temperature/fan/power + sensors on your platform. + config SENSORS_IIO_HWMON tristate "Hwmon driver that uses channels specified via iio maps" depends on IIO diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile index c48f987..199c401 100644 --- a/drivers/hwmon/Makefile +++ b/drivers/hwmon/Makefile @@ -71,6 +71,7 @@ obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o +obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o obj-$(CONFIG_SENSORS_IIO_HWMON) += iio_hwmon.o obj-$(CONFIG_SENSORS_INA209) += ina209.o obj-$(CONFIG_SENSORS_INA2XX) += ina2xx.o diff --git a/drivers/hwmon/ibmpowernv.c b/drivers/hwmon/ibmpowernv.c new file mode 100644 index 0000000..afce620 --- /dev/null +++ b/drivers/hwmon/ibmpowernv.c @@ -0,0 +1,368 @@ +/* + * IBM PowerNV platform sensors for temperature/fan/power + * Copyright (C) 2014 IBM + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. + */ + +#include <linux/init.h> +#include <linux/module.h> +#include <linux/kernel.h> +#include <linux/hwmon.h> +#include <linux/hwmon-sysfs.h> +#include <linux/of.h> +#include <linux/slab.h> + +#include <linux/platform_device.h> +#include <asm/opal.h> +#include <linux/err.h> + +#define DRVNAME "ibmpowernv" +#define MAX_ATTR_LEN 32 + +/* Sensor suffix name from DT */ +#define DT_FAULT_ATTR_SUFFIX "faulted" +#define DT_DATA_ATTR_SUFFIX "data" +#define DT_THRESHOLD_ATTR_SUFFIX "thrs" + +/* + * Enumerates all the types of sensors in the POWERNV platform and does index + * into 'struct sensor_group' + */ +enum sensors { + FAN, + AMBIENT_TEMP, + POWER_SUPPLY, + POWER_INPUT, + MAX_SENSOR_TYPE, +}; + +static struct sensor_group { + const char *name; + const char *compatible; + struct attribute_group group; + u32 attr_count; +} sensor_groups[] = { + {"fan", "ibm,opal-sensor-cooling-fan", {0}, 0}, + {"temp", "ibm,opal-sensor-amb-temp", {0}, 0}, + {"in", "ibm,opal-sensor-power-supply", {0}, 0}, + {"power", "ibm,opal-sensor-power", {0}, 0} +}; + +struct sensor_data { + u32 id; /* An opaque id of the firmware for each sensor */ + enum sensors type; + char name[MAX_ATTR_LEN]; + struct device_attribute dev_attr; +}; + +struct platform_data { + const struct attribute_group *attr_groups[MAX_SENSOR_TYPE + 1]; + u32 sensors_count; /* Total count of sensors from each group */ +}; + +/* Platform device representing all the ibmpowernv sensors */ +static struct platform_device *pdevice; + +static ssize_t show_sensor(struct device *dev, struct device_attribute *devattr, + char *buf) +{ + struct sensor_data *sdata = container_of(devattr, struct sensor_data, + dev_attr); + ssize_t ret; + u32 x; + + ret = opal_get_sensor_data(sdata->id, &x); + if (ret) { + pr_err("%s: Failed to get opal sensor data\n", __func__); + return ret; + } + + /* Convert temperature to milli-degrees */ + if (sdata->type == AMBIENT_TEMP) + x *= 1000; + /* Convert power to micro-watts */ + else if (sdata->type == POWER_INPUT) + x *= 1000000; + + return sprintf(buf, "%d\n", x); +} + +static void __init get_sensor_index_attr(const char *name, u32 *index, char *attr) +{ + char *hash_pos = strchr(name, '#'); + char *dash_pos; + u32 copy_len; + char buf[8]; + + memset(buf, 0, sizeof(buf)); + *index = 0; + *attr = '\0'; + + if (hash_pos) { + dash_pos = strchr(hash_pos, '-'); + if (dash_pos) { + copy_len = dash_pos - hash_pos - 1; + if (copy_len < sizeof(buf)) { + strncpy(buf, hash_pos + 1, copy_len); + sscanf(buf, "%d", index); + } + + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); + } + } +} + +/* + * This function translates the DT node name into the 'hwmon' attribute name. + * IBMPOWERNV device node appear like cooling-fan#2-data, amb-temp#1-thrs etc. + * which need to be mapped as fan2_input, temp1_max respectively before + * populating them inside hwmon device class.. + */ +static int __init create_hwmon_attr_name(enum sensors type, const char *node_name, + char *hwmon_attr_name) +{ + char attr_suffix[MAX_ATTR_LEN]; + char *attr_name; + u32 index; + + get_sensor_index_attr(node_name, &index, attr_suffix); + if (!index || !strlen(attr_suffix)) { + pr_info("%s: Sensor device node name is invalid, name: %s\n", + __func__, node_name); + return -EINVAL; + } + + if (!strcmp(attr_suffix, DT_FAULT_ATTR_SUFFIX)) + attr_name = "fault"; + else if(!strcmp(attr_suffix, DT_DATA_ATTR_SUFFIX)) + attr_name = "input"; + else if (!strcmp(attr_suffix, DT_THRESHOLD_ATTR_SUFFIX)) { + if (type == AMBIENT_TEMP) + attr_name = "max"; + else if (type == FAN) + attr_name = "min"; + else + return -ENOENT; + } else + return -ENOENT; + + snprintf(hwmon_attr_name, MAX_ATTR_LEN, "%s%d_%s", + sensor_groups[type].name, index, attr_name); + return 0; +} + +static int __init populate_attr_groups(struct platform_device *pdev) +{ + struct platform_data *pdata = platform_get_drvdata(pdev); + const struct attribute_group **pgroups = pdata->attr_groups; + struct device_node *opal, *np; + enum sensors type; + int err = 0; + + opal = of_find_node_by_path("/ibm,opal/sensors"); + if (!opal) { + pr_err("%s: Opal 'sensors' node not found\n", __func__); + return -ENODEV; + } + + for_each_child_of_node(opal, np) { + if (np->name == NULL) + continue; + + for (type = 0; type < MAX_SENSOR_TYPE; type++) + if (of_device_is_compatible(np, + sensor_groups[type].compatible)) { + sensor_groups[type].attr_count++; + break; + } + } + + for (type = 0; type < MAX_SENSOR_TYPE; type++) { + if (!sensor_groups[type].attr_count) + continue; + + sensor_groups[type].group.attrs = devm_kzalloc(&pdev->dev, + sizeof(struct attribute*) * + (sensor_groups[type].attr_count + 1), + GFP_KERNEL); + if (!sensor_groups[type].group.attrs) { + pr_err("%s: Failed to allocate memory for attribute" + "array\n", __func__); + err = -ENOMEM; + goto exit_put_node; + } + + pgroups[type] = &sensor_groups[type].group; + pdata->sensors_count += sensor_groups[type].attr_count; + sensor_groups[type].attr_count = 0; + } + +exit_put_node: + of_node_put(opal); + return err; +} + +/* + * Iterate through the device tree for each child of sensor node, create + * a sysfs attribute file, the file is named by translating the DT node name + * to the name required by the higher 'hwmon' driver like fan1_input, temp1_max + * etc.. + */ +static int __init create_device_attrs(struct platform_device *pdev) +{ + struct platform_data *pdata = platform_get_drvdata(pdev); + const struct attribute_group **pgroups = pdata->attr_groups; + struct device_node *opal, *np; + struct sensor_data *sdata; + const u32 *sensor_id; + enum sensors type; + u32 count = 0; + int err = 0; + + opal = of_find_node_by_path("/ibm,opal/sensors"); + if (!opal) { + pr_err("%s: Opal 'sensors' node not found\n", __func__); + return -ENODEV; + } + + sdata = devm_kzalloc(&pdev->dev, (pdata->sensors_count) * + sizeof(*sdata), GFP_KERNEL); + if (!sdata) { + pr_err("%s: Failed to allocate memory for the sensor_data", + __func__); + err = -ENOMEM; + goto exit_put_node; + } + + for_each_child_of_node(opal, np) { + if (np->name == NULL) + continue; + + for (type = 0; type < MAX_SENSOR_TYPE; type++) + if (of_device_is_compatible(np, + sensor_groups[type].compatible)) + break; + + if (type == MAX_SENSOR_TYPE) + continue; + + sensor_id = of_get_property(np, "sensor-id", NULL); + if (!sensor_id) { + pr_info("%s: %s doesn't have sensor-id\n", __func__, + np->name); + continue; + } + + sdata[count].id = *sensor_id; + sdata[count].type = type; + err = create_hwmon_attr_name(type, np->name, sdata[count].name); + if (err) + goto exit_put_node; + + sysfs_attr_init(&sdata[count].dev_attr.attr); + sdata[count].dev_attr.attr.name = sdata[count].name; + sdata[count].dev_attr.attr.mode = S_IRUGO; + sdata[count].dev_attr.show = show_sensor; + + pgroups[type]->attrs[sensor_groups[type].attr_count++] = + &sdata[count++].dev_attr.attr; + } + +exit_put_node: + of_node_put(opal); + return err; +} + +static int __init ibmpowernv_probe(struct platform_device *pdev) +{ + struct platform_data *pdata; + struct device *hwmon_dev; + int err; + + pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); + if (!pdata) + return -ENOMEM; + + platform_set_drvdata(pdev, pdata); + pdata->sensors_count = 0; + err = populate_attr_groups(pdev); + if (err) + return err; + + /* Create sysfs attribute file for each sensor found in the DT */ + err = create_device_attrs(pdev); + if (err) + return err; + + /* Finally, register with hwmon */ + hwmon_dev = devm_hwmon_device_register_with_groups(&pdev->dev, DRVNAME, + pdata, + pdata->attr_groups); + + return PTR_ERR_OR_ZERO(hwmon_dev); +} + +static struct platform_driver ibmpowernv_driver = { + .driver = { + .owner = THIS_MODULE, + .name = DRVNAME, + }, +}; + +static int __init ibmpowernv_init(void) +{ + int err; + + pdevice = platform_device_alloc(DRVNAME, 0); + if (!pdevice) { + pr_err("%s: Device allocation failed\n", __func__); + err = -ENOMEM; + goto exit; + } + + err = platform_device_add(pdevice); + if (err) { + pr_err("%s: Device addition failed (%d)\n", __func__, err); + goto exit_device_put; + } + + err = platform_driver_probe(&ibmpowernv_driver, ibmpowernv_probe); + if (err) { + pr_err("%s: Platfrom driver probe failed\n", __func__); + goto exit_device_del; + } + + return 0; + +exit_device_del: + platform_device_del(pdevice); +exit_device_put: + platform_device_put(pdevice); +exit: + return err; +} + +static void __exit ibmpowernv_exit(void) +{ + platform_driver_unregister(&ibmpowernv_driver); + platform_device_unregister(pdevice); +} + +MODULE_AUTHOR("Neelesh Gupta <neelegup@linux.vnet.ibm.com>"); +MODULE_DESCRIPTION("IBM POWERNV platform sensors"); +MODULE_LICENSE("GPL"); + +module_init(ibmpowernv_init); +module_exit(ibmpowernv_exit); ^ permalink raw reply related [flat|nested] 18+ messages in thread
* [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-19 14:38 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-19 14:38 UTC (permalink / raw) To: linuxppc-dev, linux, jdelvare, lm-sensors; +Cc: sbhat VGhpcyBwYXRjaCBhZGRzIGJhc2ljIGtlcm5lbCBlbmFibGVtZW50IGZvciByZWFkaW5nIHBvd2Vy IHZhbHVlcywgZmFuCnNwZWVkIHJwbSBhbmQgdGVtcGVyYXR1cmUgdmFsdWVzIG9uIHBvd2VybnYg cGxhdGZvcm1zIHdoaWNoIHdpbGwKYmUgZXhwb3J0ZWQgdG8gdXNlciBzcGFjZSB0aHJvdWdoIHN5 c2ZzIGludGVyZmFjZS4KClRlc3QgcmVzdWx0czoKLS0tLS0tLS0tLS0tLQpbcm9vdEB0dWwxNjNw MSB+XSMgc2Vuc29ycwppYm1wb3dlcm52LWlzYS0wMDAwCkFkYXB0ZXI6IElTQSBhZGFwdGVyCmZh bjE6ICAgICAgICA1NDg3IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQpmYW4yOiAgICAgICAgNTE1MiBS UE0gIChtaW4gPSAgICAwIFJQTSkKZmFuMzogICAgICAgIDU1OTAgUlBNICAobWluID0gICAgMCBS UE0pCmZhbjQ6ICAgICAgICA0OTYzIFJQTSAgKG1pbiA9ICAgIDAgUlBNKQpmYW41OiAgICAgICAg ICAgMCBSUE0gIChtaW4gPSAgICAwIFJQTSkKZmFuNjogICAgICAgICAgIDAgUlBNICAobWluID0g ICAgMCBSUE0pCmZhbjc6ICAgICAgICA3NDg4IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQpmYW44OiAg ICAgICAgNzk0NCBSUE0gIChtaW4gPSAgICAwIFJQTSkKdGVtcDE6ICAgICAgICArMzkuMMKwQyAg KGhpZ2ggPSAgKzAuMMKwQykKcG93ZXIxOiAgICAgIDE5Mi4wMCBXICAKCltyb290QHR1bDE2M3Ax IH5dIyBscyAvc3lzL2RldmljZXMvcGxhdGZvcm0vCmFsYXJtdGltZXIgIGlibXBvd2VybnYuMCAg cnRjLWdlbmVyaWMgIHNlcmlhbDgyNTAgIHVldmVudApbcm9vdEB0dWwxNjNwMSB+XSMgbHMgL3N5 cy9kZXZpY2VzL3BsYXRmb3JtL2libXBvd2VybnYuMC8KZHJpdmVyLyAgICBod21vbi8gICAgIG1v ZGFsaWFzICAgc3Vic3lzdGVtLyB1ZXZlbnQgICAgIApbcm9vdEB0dWwxNjNwMSB+XSMgbHMgL3N5 cy9kZXZpY2VzL3BsYXRmb3JtL2libXBvd2VybnYuMC9od21vbi9od21vbjAvCmRldmljZQkgICAg ZmFuMl9taW4JZmFuNF9taW4gICAgZmFuNl9taW4JZmFuOF9taW4gICBwb3dlcjFfaW5wdXQKZmFu MV9mYXVsdCAgZmFuM19mYXVsdAlmYW41X2ZhdWx0ICBmYW43X2ZhdWx0CWluMV9mYXVsdCAgc3Vi c3lzdGVtCmZhbjFfaW5wdXQgIGZhbjNfaW5wdXQJZmFuNV9pbnB1dCAgZmFuN19pbnB1dAlpbjJf ZmF1bHQgIHRlbXAxX2lucHV0CmZhbjFfbWluICAgIGZhbjNfbWluCWZhbjVfbWluICAgIGZhbjdf bWluCWluM19mYXVsdCAgdGVtcDFfbWF4CmZhbjJfZmF1bHQgIGZhbjRfZmF1bHQJZmFuNl9mYXVs dCAgZmFuOF9mYXVsdAlpbjRfZmF1bHQgIHVldmVudApmYW4yX2lucHV0ICBmYW40X2lucHV0CWZh bjZfaW5wdXQgIGZhbjhfaW5wdXQJbmFtZQpbcm9vdEB0dWwxNjNwMSB+XSMgCltyb290QHR1bDE2 M3AxIH5dIyBscyAvc3lzL2NsYXNzL2h3bW9uL2h3bW9uMC8KZGV2aWNlCSAgICBmYW4yX21pbglm YW40X21pbiAgICBmYW42X21pbglmYW44X21pbiAgIHBvd2VyMV9pbnB1dApmYW4xX2ZhdWx0ICBm YW4zX2ZhdWx0CWZhbjVfZmF1bHQgIGZhbjdfZmF1bHQJaW4xX2ZhdWx0ICBzdWJzeXN0ZW0KZmFu MV9pbnB1dCAgZmFuM19pbnB1dAlmYW41X2lucHV0ICBmYW43X2lucHV0CWluMl9mYXVsdCAgdGVt cDFfaW5wdXQKZmFuMV9taW4gICAgZmFuM19taW4JZmFuNV9taW4gICAgZmFuN19taW4JaW4zX2Zh dWx0ICB0ZW1wMV9tYXgKZmFuMl9mYXVsdCAgZmFuNF9mYXVsdAlmYW42X2ZhdWx0ICBmYW44X2Zh dWx0CWluNF9mYXVsdCAgdWV2ZW50CmZhbjJfaW5wdXQgIGZhbjRfaW5wdXQJZmFuNl9pbnB1dCAg ZmFuOF9pbnB1dAluYW1lCltyb290QHR1bDE2M3AxIH5dIwoKU2lnbmVkLW9mZi1ieTogTmVlbGVz aCBHdXB0YSA8bmVlbGVndXBAbGludXgudm5ldC5pYm0uY29tPgotLS0KCkNoYW5nZXMgaW4gdjIK PT09PT09PT09PT09PQotIEdlbmVyaWMgdXNlIG9mIGRldm1fKiBmdW5jdGlvbnMgaW4gaHdtb24g bGlrZSB1c2luZyBkZXZtX2t6YWxsb2MoKSBmb3IgZHluYW1pYwogIG1lbW9yeSByZXF1ZXN0LCBh dm9pZGluZyB0aGUgbmVlZCB0byBleHBsaWNpdCBmcmVlIG9mIG1lbW9yeS4KICBBZGRpbmcgJ3N0 cnVjdCBhdHRyaWJ1dGVfZ3JvdXAnIGFzIG1lbWJlciBvZiBwbGF0Zm9ybSBkYXRhIHN0cnVjdHVy ZSB0byBiZQogIHBvcHVsYXRlZCBhbmQgdGhlbiBwYXNzZWQgdG8gZGV2bV9od21vbl9kZXZpY2Vf cmVnaXN0ZXJfd2l0aF9ncm91cHMoKS4KCiAgTm90ZTogSGF2aW5nIGFuIGFycmF5IG9mIHBvaW50 ZXJzIG9mICdhdHRyaWJ1dGVfZ3JvdXAnIGFuZCBlYWNoIGdyb3VwCiAgY29ycmVzcG9uZHMgdG8g J2VudW0gc2Vuc29ycycgdHlwZS4gTm90IGNvbXBsZXRlbHkgc3VyZSwgaWYgaXQncyBpZGVhbCBv cgogIGNvdWxkIGhhdmUganVzdCBvbmUgZ3JvdXAgcG9wdWxhdGVkIHdpdGggYXR0cmlidXRlcyBv ZiBzZW5zb3IgdHlwZXM/CgotICdpYm1wb3dlcm52JyBpcyBub3QgaG90LXBsdWdnYWJsZSBkZXZp Y2Ugc28gbW92aW5nICdwbGF0Zm9ybV9kcml2ZXInIGNhbGxiYWNrCiAgZnVuY3Rpb24gKHByb2Jl KSBhcyBwYXJ0IG9mIF9faW5pdCBjb2RlLgotIEZpeGVkIGlzc3VlcyByZWxhdGVkIHRvIGNvZGlu ZyBzdHlsZS4KLSBPdGhlciBnZW5lcmFsIGNvbW1lbnRzIGluIHYxLgoKIGRyaXZlcnMvaHdtb24v S2NvbmZpZyAgICAgIHwgICAgOCArCiBkcml2ZXJzL2h3bW9uL01ha2VmaWxlICAgICB8ICAgIDEg CiBkcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYyB8ICAzNjggKysrKysrKysrKysrKysrKysrKysr KysrKysrKysrKysrKysrKysrKysrKysKIDMgZmlsZXMgY2hhbmdlZCwgMzc3IGluc2VydGlvbnMo KykKIGNyZWF0ZSBtb2RlIDEwMDY0NCBkcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwoKZGlmZiAt LWdpdCBhL2RyaXZlcnMvaHdtb24vS2NvbmZpZyBiL2RyaXZlcnMvaHdtb24vS2NvbmZpZwppbmRl eCBiYzE5NmY0Li4zZTMwOGZhIDEwMDY0NAotLS0gYS9kcml2ZXJzL2h3bW9uL0tjb25maWcKKysr IGIvZHJpdmVycy9od21vbi9LY29uZmlnCkBAIC01NTQsNiArNTU0LDE0IEBAIGNvbmZpZyBTRU5T T1JTX0lCTVBFWAogCSAgVGhpcyBkcml2ZXIgY2FuIGFsc28gYmUgYnVpbHQgYXMgYSBtb2R1bGUu ICBJZiBzbywgdGhlIG1vZHVsZQogCSAgd2lsbCBiZSBjYWxsZWQgaWJtcGV4LgogCitjb25maWcg U0VOU09SU19JQk1QT1dFUk5WCisJdHJpc3RhdGUgIklCTSBQT1dFUk5WIHBsYXRmb3JtIHNlbnNv cnMiCisJZGVwZW5kcyBvbiBQUENfUE9XRVJOVgorCWRlZmF1bHQgeQorCWhlbHAKKwkgIElmIHlv dSBzYXkgeWVzIGhlcmUgeW91IGdldCBzdXBwb3J0IGZvciB0aGUgdGVtcGVyYXR1cmUvZmFuL3Bv d2VyCisJICBzZW5zb3JzIG9uIHlvdXIgcGxhdGZvcm0uCisKIGNvbmZpZyBTRU5TT1JTX0lJT19I V01PTgogCXRyaXN0YXRlICJId21vbiBkcml2ZXIgdGhhdCB1c2VzIGNoYW5uZWxzIHNwZWNpZmll ZCB2aWEgaWlvIG1hcHMiCiAJZGVwZW5kcyBvbiBJSU8KZGlmZiAtLWdpdCBhL2RyaXZlcnMvaHdt b24vTWFrZWZpbGUgYi9kcml2ZXJzL2h3bW9uL01ha2VmaWxlCmluZGV4IGM0OGY5ODcuLjE5OWM0 MDEgMTAwNjQ0Ci0tLSBhL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUKKysrIGIvZHJpdmVycy9od21v bi9NYWtlZmlsZQpAQCAtNzEsNiArNzEsNyBAQCBvYmotJChDT05GSUdfU0VOU09SU19VTFRSQTQ1 KQkrPSB1bHRyYTQ1X2Vudi5vCiBvYmotJChDT05GSUdfU0VOU09SU19JNUtfQU1CKQkrPSBpNWtf YW1iLm8KIG9iai0kKENPTkZJR19TRU5TT1JTX0lCTUFFTSkJKz0gaWJtYWVtLm8KIG9iai0kKENP TkZJR19TRU5TT1JTX0lCTVBFWCkJKz0gaWJtcGV4Lm8KK29iai0kKENPTkZJR19TRU5TT1JTX0lC TVBPV0VSTlYpKz0gaWJtcG93ZXJudi5vCiBvYmotJChDT05GSUdfU0VOU09SU19JSU9fSFdNT04p ICs9IGlpb19od21vbi5vCiBvYmotJChDT05GSUdfU0VOU09SU19JTkEyMDkpCSs9IGluYTIwOS5v CiBvYmotJChDT05GSUdfU0VOU09SU19JTkEyWFgpCSs9IGluYTJ4eC5vCmRpZmYgLS1naXQgYS9k cml2ZXJzL2h3bW9uL2libXBvd2VybnYuYyBiL2RyaXZlcnMvaHdtb24vaWJtcG93ZXJudi5jCm5l dyBmaWxlIG1vZGUgMTAwNjQ0CmluZGV4IDAwMDAwMDAuLmFmY2U2MjAKLS0tIC9kZXYvbnVsbAor KysgYi9kcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwpAQCAtMCwwICsxLDM2OCBAQAorLyoKKyAq IElCTSBQb3dlck5WIHBsYXRmb3JtIHNlbnNvcnMgZm9yIHRlbXBlcmF0dXJlL2Zhbi9wb3dlcgor ICogQ29weXJpZ2h0IChDKSAyMDE0IElCTQorICoKKyAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNv ZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CisgKiBpdCB1bmRl ciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hl ZCBieQorICogdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMiBv ZiB0aGUgTGljZW5zZSwgb3IKKyAqIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24u CisgKgorICogVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQg d2lsbCBiZSB1c2VmdWwsCisgKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZl biB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgorICogTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1Mg Rk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiAgU2VlIHRoZQorICogR05VIEdlbmVyYWwgUHVibGlj IExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KKyAqCisgKiBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2 ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQorICogYWxvbmcgd2l0 aCB0aGlzIHByb2dyYW0uCisgKi8KKworI2luY2x1ZGUgPGxpbnV4L2luaXQuaD4KKyNpbmNsdWRl IDxsaW51eC9tb2R1bGUuaD4KKyNpbmNsdWRlIDxsaW51eC9rZXJuZWwuaD4KKyNpbmNsdWRlIDxs aW51eC9od21vbi5oPgorI2luY2x1ZGUgPGxpbnV4L2h3bW9uLXN5c2ZzLmg+CisjaW5jbHVkZSA8 bGludXgvb2YuaD4KKyNpbmNsdWRlIDxsaW51eC9zbGFiLmg+CisKKyNpbmNsdWRlIDxsaW51eC9w bGF0Zm9ybV9kZXZpY2UuaD4KKyNpbmNsdWRlIDxhc20vb3BhbC5oPgorI2luY2x1ZGUgPGxpbnV4 L2Vyci5oPgorCisjZGVmaW5lIERSVk5BTUUJCSJpYm1wb3dlcm52IgorI2RlZmluZSBNQVhfQVRU Ul9MRU4JMzIKKworLyogU2Vuc29yIHN1ZmZpeCBuYW1lIGZyb20gRFQgKi8KKyNkZWZpbmUgRFRf RkFVTFRfQVRUUl9TVUZGSVgJCSJmYXVsdGVkIgorI2RlZmluZSBEVF9EQVRBX0FUVFJfU1VGRklY CQkiZGF0YSIKKyNkZWZpbmUgRFRfVEhSRVNIT0xEX0FUVFJfU1VGRklYCSJ0aHJzIgorCisvKgor ICogRW51bWVyYXRlcyBhbGwgdGhlIHR5cGVzIG9mIHNlbnNvcnMgaW4gdGhlIFBPV0VSTlYgcGxh dGZvcm0gYW5kIGRvZXMgaW5kZXgKKyAqIGludG8gJ3N0cnVjdCBzZW5zb3JfZ3JvdXAnCisgKi8K K2VudW0gc2Vuc29ycyB7CisJRkFOLAorCUFNQklFTlRfVEVNUCwKKwlQT1dFUl9TVVBQTFksCisJ UE9XRVJfSU5QVVQsCisJTUFYX1NFTlNPUl9UWVBFLAorfTsKKworc3RhdGljIHN0cnVjdCBzZW5z b3JfZ3JvdXAgeworCWNvbnN0IGNoYXIgKm5hbWU7CisJY29uc3QgY2hhciAqY29tcGF0aWJsZTsK KwlzdHJ1Y3QgYXR0cmlidXRlX2dyb3VwIGdyb3VwOworCXUzMiBhdHRyX2NvdW50OworfSBzZW5z b3JfZ3JvdXBzW10gPSB7CisJeyJmYW4iLCAiaWJtLG9wYWwtc2Vuc29yLWNvb2xpbmctZmFuIiwg ezB9LCAwfSwKKwl7InRlbXAiLCAiaWJtLG9wYWwtc2Vuc29yLWFtYi10ZW1wIiwgezB9LCAwfSwK Kwl7ImluIiwgImlibSxvcGFsLXNlbnNvci1wb3dlci1zdXBwbHkiLCB7MH0sIDB9LAorCXsicG93 ZXIiLCAiaWJtLG9wYWwtc2Vuc29yLXBvd2VyIiwgezB9LCAwfQorfTsKKworc3RydWN0IHNlbnNv cl9kYXRhIHsKKwl1MzIgaWQ7IC8qIEFuIG9wYXF1ZSBpZCBvZiB0aGUgZmlybXdhcmUgZm9yIGVh Y2ggc2Vuc29yICovCisJZW51bSBzZW5zb3JzIHR5cGU7CisJY2hhciBuYW1lW01BWF9BVFRSX0xF Tl07CisJc3RydWN0IGRldmljZV9hdHRyaWJ1dGUgZGV2X2F0dHI7Cit9OworCitzdHJ1Y3QgcGxh dGZvcm1fZGF0YSB7CisJY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqYXR0cl9ncm91cHNb TUFYX1NFTlNPUl9UWVBFICsgMV07CisJdTMyIHNlbnNvcnNfY291bnQ7IC8qIFRvdGFsIGNvdW50 IG9mIHNlbnNvcnMgZnJvbSBlYWNoIGdyb3VwICovCit9OworCisvKiBQbGF0Zm9ybSBkZXZpY2Ug cmVwcmVzZW50aW5nIGFsbCB0aGUgaWJtcG93ZXJudiBzZW5zb3JzICovCitzdGF0aWMgc3RydWN0 IHBsYXRmb3JtX2RldmljZSAqcGRldmljZTsKKworc3RhdGljIHNzaXplX3Qgc2hvd19zZW5zb3Io c3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqZGV2YXR0ciwKKwkJ CSAgIGNoYXIgKmJ1ZikKK3sKKwlzdHJ1Y3Qgc2Vuc29yX2RhdGEgKnNkYXRhID0gY29udGFpbmVy X29mKGRldmF0dHIsIHN0cnVjdCBzZW5zb3JfZGF0YSwKKwkJCQkJCSBkZXZfYXR0cik7CisJc3Np emVfdCByZXQ7CisJdTMyIHg7CisKKwlyZXQgPSBvcGFsX2dldF9zZW5zb3JfZGF0YShzZGF0YS0+ aWQsICZ4KTsKKwlpZiAocmV0KSB7CisJCXByX2VycigiJXM6IEZhaWxlZCB0byBnZXQgb3BhbCBz ZW5zb3IgZGF0YVxuIiwgX19mdW5jX18pOworCQlyZXR1cm4gcmV0OworCX0KKworCS8qIENvbnZl cnQgdGVtcGVyYXR1cmUgdG8gbWlsbGktZGVncmVlcyAqLworCWlmIChzZGF0YS0+dHlwZSA9PSBB TUJJRU5UX1RFTVApCisJCXggKj0gMTAwMDsKKwkvKiBDb252ZXJ0IHBvd2VyIHRvIG1pY3JvLXdh dHRzICovCisJZWxzZSBpZiAoc2RhdGEtPnR5cGUgPT0gUE9XRVJfSU5QVVQpCisJCXggKj0gMTAw MDAwMDsKKworCXJldHVybiBzcHJpbnRmKGJ1ZiwgIiVkXG4iLCB4KTsKK30KKworc3RhdGljIHZv aWQgX19pbml0IGdldF9zZW5zb3JfaW5kZXhfYXR0cihjb25zdCBjaGFyICpuYW1lLCB1MzIgKmlu ZGV4LCBjaGFyICphdHRyKQoreworCWNoYXIgKmhhc2hfcG9zID0gc3RyY2hyKG5hbWUsICcjJyk7 CisJY2hhciAqZGFzaF9wb3M7CisJdTMyIGNvcHlfbGVuOworCWNoYXIgYnVmWzhdOworCisJbWVt c2V0KGJ1ZiwgMCwgc2l6ZW9mKGJ1ZikpOworCSppbmRleCA9IDA7CisJKmF0dHIgPSAnXDAnOwor CisJaWYgKGhhc2hfcG9zKSB7CisJCWRhc2hfcG9zID0gc3RyY2hyKGhhc2hfcG9zLCAnLScpOwor CQlpZiAoZGFzaF9wb3MpIHsKKwkJCWNvcHlfbGVuID0gZGFzaF9wb3MgLSBoYXNoX3BvcyAtIDE7 CisJCQlpZiAoY29weV9sZW4gPCBzaXplb2YoYnVmKSkgeworCQkJCXN0cm5jcHkoYnVmLCBoYXNo X3BvcyArIDEsIGNvcHlfbGVuKTsKKwkJCQlzc2NhbmYoYnVmLCAiJWQiLCBpbmRleCk7CisJCQl9 CisKKwkJCXN0cm5jcHkoYXR0ciwgZGFzaF9wb3MgKyAxLCBNQVhfQVRUUl9MRU4pOworCQl9CisJ fQorfQorCisvKgorICogVGhpcyBmdW5jdGlvbiB0cmFuc2xhdGVzIHRoZSBEVCBub2RlIG5hbWUg aW50byB0aGUgJ2h3bW9uJyBhdHRyaWJ1dGUgbmFtZS4KKyAqIElCTVBPV0VSTlYgZGV2aWNlIG5v ZGUgYXBwZWFyIGxpa2UgY29vbGluZy1mYW4jMi1kYXRhLCBhbWItdGVtcCMxLXRocnMgZXRjLgor ICogd2hpY2ggbmVlZCB0byBiZSBtYXBwZWQgYXMgZmFuMl9pbnB1dCwgdGVtcDFfbWF4IHJlc3Bl Y3RpdmVseSBiZWZvcmUKKyAqIHBvcHVsYXRpbmcgdGhlbSBpbnNpZGUgaHdtb24gZGV2aWNlIGNs YXNzLi4KKyAqLworc3RhdGljIGludCBfX2luaXQgY3JlYXRlX2h3bW9uX2F0dHJfbmFtZShlbnVt IHNlbnNvcnMgdHlwZSwgY29uc3QgY2hhciAqbm9kZV9uYW1lLAorCQkJCSAgY2hhciAqaHdtb25f YXR0cl9uYW1lKQoreworCWNoYXIgYXR0cl9zdWZmaXhbTUFYX0FUVFJfTEVOXTsKKwljaGFyICph dHRyX25hbWU7CisJdTMyIGluZGV4OworCisJZ2V0X3NlbnNvcl9pbmRleF9hdHRyKG5vZGVfbmFt ZSwgJmluZGV4LCBhdHRyX3N1ZmZpeCk7CisJaWYgKCFpbmRleCB8fCAhc3RybGVuKGF0dHJfc3Vm Zml4KSkgeworCQlwcl9pbmZvKCIlczogU2Vuc29yIGRldmljZSBub2RlIG5hbWUgaXMgaW52YWxp ZCwgbmFtZTogJXNcbiIsCisJCQkJX19mdW5jX18sIG5vZGVfbmFtZSk7CisJCXJldHVybiAtRUlO VkFMOworCX0KKworCWlmICghc3RyY21wKGF0dHJfc3VmZml4LCBEVF9GQVVMVF9BVFRSX1NVRkZJ WCkpCisJCWF0dHJfbmFtZSA9ICJmYXVsdCI7CisJZWxzZSBpZighc3RyY21wKGF0dHJfc3VmZml4 LCBEVF9EQVRBX0FUVFJfU1VGRklYKSkKKwkJYXR0cl9uYW1lID0gImlucHV0IjsKKwllbHNlIGlm ICghc3RyY21wKGF0dHJfc3VmZml4LCBEVF9USFJFU0hPTERfQVRUUl9TVUZGSVgpKSB7CisJCWlm ICh0eXBlID09IEFNQklFTlRfVEVNUCkKKwkJCWF0dHJfbmFtZSA9ICJtYXgiOworCQllbHNlIGlm ICh0eXBlID09IEZBTikKKwkJCWF0dHJfbmFtZSA9ICJtaW4iOworCQllbHNlCisJCQlyZXR1cm4g LUVOT0VOVDsKKwl9IGVsc2UKKwkJcmV0dXJuIC1FTk9FTlQ7CisKKwlzbnByaW50Zihod21vbl9h dHRyX25hbWUsIE1BWF9BVFRSX0xFTiwgIiVzJWRfJXMiLAorCQkJc2Vuc29yX2dyb3Vwc1t0eXBl XS5uYW1lLCBpbmRleCwgYXR0cl9uYW1lKTsKKwlyZXR1cm4gMDsKK30KKworc3RhdGljIGludCBf X2luaXQgcG9wdWxhdGVfYXR0cl9ncm91cHMoc3RydWN0IHBsYXRmb3JtX2RldmljZSAqcGRldikK K3sKKwlzdHJ1Y3QgcGxhdGZvcm1fZGF0YSAqcGRhdGEgPSBwbGF0Zm9ybV9nZXRfZHJ2ZGF0YShw ZGV2KTsKKwljb25zdCBzdHJ1Y3QgYXR0cmlidXRlX2dyb3VwICoqcGdyb3VwcyA9IHBkYXRhLT5h dHRyX2dyb3VwczsKKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpucDsKKwllbnVtIHNlbnNv cnMgdHlwZTsKKwlpbnQgZXJyID0gMDsKKworCW9wYWwgPSBvZl9maW5kX25vZGVfYnlfcGF0aCgi L2libSxvcGFsL3NlbnNvcnMiKTsKKyAgICAgICAgaWYgKCFvcGFsKSB7CisJCXByX2VycigiJXM6 IE9wYWwgJ3NlbnNvcnMnIG5vZGUgbm90IGZvdW5kXG4iLCBfX2Z1bmNfXyk7CisJCXJldHVybiAt RU5PREVWOworICAgICAgICB9CisKKwlmb3JfZWFjaF9jaGlsZF9vZl9ub2RlKG9wYWwsIG5wKSB7 CisJCWlmIChucC0+bmFtZSA9PSBOVUxMKQorCQkJY29udGludWU7CisKKwkJZm9yICh0eXBlID0g MDsgdHlwZSA8IE1BWF9TRU5TT1JfVFlQRTsgdHlwZSsrKQorCQkJaWYgKG9mX2RldmljZV9pc19j b21wYXRpYmxlKG5wLAorCQkJCXNlbnNvcl9ncm91cHNbdHlwZV0uY29tcGF0aWJsZSkpIHsKKwkJ CQlzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQrKzsKKwkJCQlicmVhazsKKwkJCX0KKwl9 CisKKwlmb3IgKHR5cGUgPSAwOyB0eXBlIDwgTUFYX1NFTlNPUl9UWVBFOyB0eXBlKyspIHsKKwkJ aWYgKCFzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQpCisJCQljb250aW51ZTsKKworCQlz ZW5zb3JfZ3JvdXBzW3R5cGVdLmdyb3VwLmF0dHJzID0gZGV2bV9remFsbG9jKCZwZGV2LT5kZXYs CisJCQkJCXNpemVvZihzdHJ1Y3QgYXR0cmlidXRlKikgKgorCQkJCQkoc2Vuc29yX2dyb3Vwc1t0 eXBlXS5hdHRyX2NvdW50ICsgMSksCisJCQkJCUdGUF9LRVJORUwpOworCQlpZiAoIXNlbnNvcl9n cm91cHNbdHlwZV0uZ3JvdXAuYXR0cnMpIHsKKwkJCXByX2VycigiJXM6IEZhaWxlZCB0byBhbGxv Y2F0ZSBtZW1vcnkgZm9yIGF0dHJpYnV0ZSIKKwkJCQkJImFycmF5XG4iLCBfX2Z1bmNfXyk7CisJ CQllcnIgPSAtRU5PTUVNOworCQkJZ290byBleGl0X3B1dF9ub2RlOworCQl9CisKKwkJcGdyb3Vw c1t0eXBlXSA9ICZzZW5zb3JfZ3JvdXBzW3R5cGVdLmdyb3VwOworCQlwZGF0YS0+c2Vuc29yc19j b3VudCArPSBzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQ7CisJCXNlbnNvcl9ncm91cHNb dHlwZV0uYXR0cl9jb3VudCA9IDA7CisJfQorCitleGl0X3B1dF9ub2RlOgorCW9mX25vZGVfcHV0 KG9wYWwpOworCXJldHVybiBlcnI7Cit9CisKKy8qCisgKiBJdGVyYXRlIHRocm91Z2ggdGhlIGRl dmljZSB0cmVlIGZvciBlYWNoIGNoaWxkIG9mIHNlbnNvciBub2RlLCBjcmVhdGUKKyAqIGEgc3lz ZnMgYXR0cmlidXRlIGZpbGUsIHRoZSBmaWxlIGlzIG5hbWVkIGJ5IHRyYW5zbGF0aW5nIHRoZSBE VCBub2RlIG5hbWUKKyAqIHRvIHRoZSBuYW1lIHJlcXVpcmVkIGJ5IHRoZSBoaWdoZXIgJ2h3bW9u JyBkcml2ZXIgbGlrZSBmYW4xX2lucHV0LCB0ZW1wMV9tYXgKKyAqIGV0Yy4uCisgKi8KK3N0YXRp YyBpbnQgX19pbml0IGNyZWF0ZV9kZXZpY2VfYXR0cnMoc3RydWN0IHBsYXRmb3JtX2RldmljZSAq cGRldikKK3sKKwlzdHJ1Y3QgcGxhdGZvcm1fZGF0YSAqcGRhdGEgPSBwbGF0Zm9ybV9nZXRfZHJ2 ZGF0YShwZGV2KTsKKwljb25zdCBzdHJ1Y3QgYXR0cmlidXRlX2dyb3VwICoqcGdyb3VwcyA9IHBk YXRhLT5hdHRyX2dyb3VwczsKKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpucDsKKwlzdHJ1 Y3Qgc2Vuc29yX2RhdGEgKnNkYXRhOworCWNvbnN0IHUzMiAqc2Vuc29yX2lkOworCWVudW0gc2Vu c29ycyB0eXBlOworCXUzMiBjb3VudCA9IDA7CisJaW50IGVyciA9IDA7CisKKwlvcGFsID0gb2Zf ZmluZF9ub2RlX2J5X3BhdGgoIi9pYm0sb3BhbC9zZW5zb3JzIik7CisgICAgICAgIGlmICghb3Bh bCkgeworCQlwcl9lcnIoIiVzOiBPcGFsICdzZW5zb3JzJyBub2RlIG5vdCBmb3VuZFxuIiwgX19m dW5jX18pOworCQlyZXR1cm4gLUVOT0RFVjsKKyAgICAgICAgfQorCisJc2RhdGEgPSBkZXZtX2t6 YWxsb2MoJnBkZXYtPmRldiwgKHBkYXRhLT5zZW5zb3JzX2NvdW50KSAqCisJCQkgICAgIHNpemVv Zigqc2RhdGEpLCBHRlBfS0VSTkVMKTsKKwlpZiAoIXNkYXRhKSB7CisJCXByX2VycigiJXM6IEZh aWxlZCB0byBhbGxvY2F0ZSBtZW1vcnkgZm9yIHRoZSBzZW5zb3JfZGF0YSIsCisJCQkJX19mdW5j X18pOworCQllcnIgPSAtRU5PTUVNOworCQlnb3RvIGV4aXRfcHV0X25vZGU7CisJfQorCisJZm9y X2VhY2hfY2hpbGRfb2Zfbm9kZShvcGFsLCBucCkgeworICAgICAgICAgICAgICAgIGlmIChucC0+ bmFtZSA9PSBOVUxMKQorICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7CisKKwkJZm9y ICh0eXBlID0gMDsgdHlwZSA8IE1BWF9TRU5TT1JfVFlQRTsgdHlwZSsrKQorCQkJaWYgKG9mX2Rl dmljZV9pc19jb21wYXRpYmxlKG5wLAorCQkJCQlzZW5zb3JfZ3JvdXBzW3R5cGVdLmNvbXBhdGli bGUpKQorCQkJCWJyZWFrOworCisJCWlmICh0eXBlID09IE1BWF9TRU5TT1JfVFlQRSkKKwkJCWNv bnRpbnVlOworCisJCXNlbnNvcl9pZCA9IG9mX2dldF9wcm9wZXJ0eShucCwgInNlbnNvci1pZCIs IE5VTEwpOworCQlpZiAoIXNlbnNvcl9pZCkgeworCQkJcHJfaW5mbygiJXM6ICVzIGRvZXNuJ3Qg aGF2ZSBzZW5zb3ItaWRcbiIsIF9fZnVuY19fLAorCQkJCW5wLT5uYW1lKTsKKwkJCWNvbnRpbnVl OworCQl9CisKKwkJc2RhdGFbY291bnRdLmlkID0gKnNlbnNvcl9pZDsKKwkJc2RhdGFbY291bnRd LnR5cGUgPSB0eXBlOworCQllcnIgPSBjcmVhdGVfaHdtb25fYXR0cl9uYW1lKHR5cGUsIG5wLT5u YW1lLCBzZGF0YVtjb3VudF0ubmFtZSk7CisJCWlmIChlcnIpCisJCQlnb3RvIGV4aXRfcHV0X25v ZGU7CisKKwkJc3lzZnNfYXR0cl9pbml0KCZzZGF0YVtjb3VudF0uZGV2X2F0dHIuYXR0cik7CisJ CXNkYXRhW2NvdW50XS5kZXZfYXR0ci5hdHRyLm5hbWUgPSBzZGF0YVtjb3VudF0ubmFtZTsKKwkJ c2RhdGFbY291bnRdLmRldl9hdHRyLmF0dHIubW9kZSA9IFNfSVJVR087CisJCXNkYXRhW2NvdW50 XS5kZXZfYXR0ci5zaG93ID0gc2hvd19zZW5zb3I7CisKKwkJcGdyb3Vwc1t0eXBlXS0+YXR0cnNb c2Vuc29yX2dyb3Vwc1t0eXBlXS5hdHRyX2NvdW50KytdID0KKwkJCQkmc2RhdGFbY291bnQrK10u ZGV2X2F0dHIuYXR0cjsKKwl9CisKK2V4aXRfcHV0X25vZGU6CisJb2Zfbm9kZV9wdXQob3BhbCk7 CisJcmV0dXJuIGVycjsKK30KKworc3RhdGljIGludCBfX2luaXQgaWJtcG93ZXJudl9wcm9iZShz dHJ1Y3QgcGxhdGZvcm1fZGV2aWNlICpwZGV2KQoreworCXN0cnVjdCBwbGF0Zm9ybV9kYXRhICpw ZGF0YTsKKwlzdHJ1Y3QgZGV2aWNlICpod21vbl9kZXY7CisJaW50IGVycjsKKworCXBkYXRhID0g ZGV2bV9remFsbG9jKCZwZGV2LT5kZXYsIHNpemVvZigqcGRhdGEpLCBHRlBfS0VSTkVMKTsKKwlp ZiAoIXBkYXRhKQorCQlyZXR1cm4gLUVOT01FTTsKKworCXBsYXRmb3JtX3NldF9kcnZkYXRhKHBk ZXYsIHBkYXRhKTsKKwlwZGF0YS0+c2Vuc29yc19jb3VudCA9IDA7CisJZXJyID0gcG9wdWxhdGVf YXR0cl9ncm91cHMocGRldik7CisJaWYgKGVycikKKwkJcmV0dXJuIGVycjsKKworCS8qIENyZWF0 ZSBzeXNmcyBhdHRyaWJ1dGUgZmlsZSBmb3IgZWFjaCBzZW5zb3IgZm91bmQgaW4gdGhlIERUICov CisJZXJyID0gY3JlYXRlX2RldmljZV9hdHRycyhwZGV2KTsKKwlpZiAoZXJyKQorCQlyZXR1cm4g ZXJyOworCisJLyogRmluYWxseSwgcmVnaXN0ZXIgd2l0aCBod21vbiAqLworCWh3bW9uX2RldiA9 IGRldm1faHdtb25fZGV2aWNlX3JlZ2lzdGVyX3dpdGhfZ3JvdXBzKCZwZGV2LT5kZXYsIERSVk5B TUUsCisJCQkJCQkJICAgcGRhdGEsCisJCQkJCQkJICAgcGRhdGEtPmF0dHJfZ3JvdXBzKTsKKwor CXJldHVybiBQVFJfRVJSX09SX1pFUk8oaHdtb25fZGV2KTsKK30KKworc3RhdGljIHN0cnVjdCBw bGF0Zm9ybV9kcml2ZXIgaWJtcG93ZXJudl9kcml2ZXIgPSB7CisJLmRyaXZlciA9IHsKKwkJLm93 bmVyID0gVEhJU19NT0RVTEUsCisJCS5uYW1lID0gRFJWTkFNRSwKKwl9LAorfTsKKworc3RhdGlj IGludCBfX2luaXQgaWJtcG93ZXJudl9pbml0KHZvaWQpCit7CisJaW50IGVycjsKKworCXBkZXZp Y2UgPSBwbGF0Zm9ybV9kZXZpY2VfYWxsb2MoRFJWTkFNRSwgMCk7CisJaWYgKCFwZGV2aWNlKSB7 CisJCXByX2VycigiJXM6IERldmljZSBhbGxvY2F0aW9uIGZhaWxlZFxuIiwgX19mdW5jX18pOwor CQllcnIgPSAtRU5PTUVNOworCQlnb3RvIGV4aXQ7CisJfQorCisJZXJyID0gcGxhdGZvcm1fZGV2 aWNlX2FkZChwZGV2aWNlKTsKKwlpZiAoZXJyKSB7CisJCXByX2VycigiJXM6IERldmljZSBhZGRp dGlvbiBmYWlsZWQgKCVkKVxuIiwgX19mdW5jX18sIGVycik7CisJCWdvdG8gZXhpdF9kZXZpY2Vf cHV0OworCX0KKworCWVyciA9IHBsYXRmb3JtX2RyaXZlcl9wcm9iZSgmaWJtcG93ZXJudl9kcml2 ZXIsIGlibXBvd2VybnZfcHJvYmUpOworCWlmIChlcnIpIHsKKwkJcHJfZXJyKCIlczogUGxhdGZy b20gZHJpdmVyIHByb2JlIGZhaWxlZFxuIiwgX19mdW5jX18pOworCQlnb3RvIGV4aXRfZGV2aWNl X2RlbDsKKwl9CisKKwlyZXR1cm4gMDsKKworZXhpdF9kZXZpY2VfZGVsOgorCXBsYXRmb3JtX2Rl dmljZV9kZWwocGRldmljZSk7CitleGl0X2RldmljZV9wdXQ6CisJcGxhdGZvcm1fZGV2aWNlX3B1 dChwZGV2aWNlKTsKK2V4aXQ6CisJcmV0dXJuIGVycjsKK30KKworc3RhdGljIHZvaWQgX19leGl0 IGlibXBvd2VybnZfZXhpdCh2b2lkKQoreworCXBsYXRmb3JtX2RyaXZlcl91bnJlZ2lzdGVyKCZp Ym1wb3dlcm52X2RyaXZlcik7CisJcGxhdGZvcm1fZGV2aWNlX3VucmVnaXN0ZXIocGRldmljZSk7 Cit9CisKK01PRFVMRV9BVVRIT1IoIk5lZWxlc2ggR3VwdGEgPG5lZWxlZ3VwQGxpbnV4LnZuZXQu aWJtLmNvbT4iKTsKK01PRFVMRV9ERVNDUklQVElPTigiSUJNIFBPV0VSTlYgcGxhdGZvcm0gc2Vu c29ycyIpOworTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOworCittb2R1bGVfaW5pdChpYm1wb3dlcm52 X2luaXQpOworbW9kdWxlX2V4aXQoaWJtcG93ZXJudl9leGl0KTsKCgpfX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fXwpsbS1zZW5zb3JzIG1haWxpbmcgbGlzdAps bS1zZW5zb3JzQGxtLXNlbnNvcnMub3JnCmh0dHA6Ly9saXN0cy5sbS1zZW5zb3JzLm9yZy9tYWls bWFuL2xpc3RpbmZvL2xtLXNlbnNvcnM ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-19 14:38 ` [lm-sensors] " Neelesh Gupta @ 2014-05-26 6:34 ` Neelesh Gupta -1 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-26 6:22 UTC (permalink / raw) To: linuxppc-dev, linux, jdelvare, lm-sensors; +Cc: sbhat [-- Attachment #1: Type: text/plain, Size: 15027 bytes --] Any updates on the patch. - Neelesh On 05/19/2014 07:56 PM, Neelesh Gupta wrote: > This patch adds basic kernel enablement for reading power values, fan > speed rpm and temperature values on powernv platforms which will > be exported to user space through sysfs interface. > > Test results: > ------------- > [root@tul163p1 ~]# sensors > ibmpowernv-isa-0000 > Adapter: ISA adapter > fan1: 5487 RPM (min = 0 RPM) > fan2: 5152 RPM (min = 0 RPM) > fan3: 5590 RPM (min = 0 RPM) > fan4: 4963 RPM (min = 0 RPM) > fan5: 0 RPM (min = 0 RPM) > fan6: 0 RPM (min = 0 RPM) > fan7: 7488 RPM (min = 0 RPM) > fan8: 7944 RPM (min = 0 RPM) > temp1: +39.0°C (high = +0.0°C) > power1: 192.00 W > > [root@tul163p1 ~]# ls /sys/devices/platform/ > alarmtimer ibmpowernv.0 rtc-generic serial8250 uevent > [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/ > driver/ hwmon/ modalias subsystem/ uevent > [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/hwmon/hwmon0/ > device fan2_min fan4_min fan6_min fan8_min power1_input > fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem > fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input > fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max > fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent > fan2_input fan4_input fan6_input fan8_input name > [root@tul163p1 ~]# > [root@tul163p1 ~]# ls /sys/class/hwmon/hwmon0/ > device fan2_min fan4_min fan6_min fan8_min power1_input > fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem > fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input > fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max > fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent > fan2_input fan4_input fan6_input fan8_input name > [root@tul163p1 ~]# > > Signed-off-by: Neelesh Gupta <neelegup@linux.vnet.ibm.com> > --- > > Changes in v2 > ============= > - Generic use of devm_* functions in hwmon like using devm_kzalloc() for dynamic > memory request, avoiding the need to explicit free of memory. > Adding 'struct attribute_group' as member of platform data structure to be > populated and then passed to devm_hwmon_device_register_with_groups(). > > Note: Having an array of pointers of 'attribute_group' and each group > corresponds to 'enum sensors' type. Not completely sure, if it's ideal or > could have just one group populated with attributes of sensor types? > > - 'ibmpowernv' is not hot-pluggable device so moving 'platform_driver' callback > function (probe) as part of __init code. > - Fixed issues related to coding style. > - Other general comments in v1. > > drivers/hwmon/Kconfig | 8 + > drivers/hwmon/Makefile | 1 > drivers/hwmon/ibmpowernv.c | 368 ++++++++++++++++++++++++++++++++++++++++++++ > 3 files changed, 377 insertions(+) > create mode 100644 drivers/hwmon/ibmpowernv.c > > diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig > index bc196f4..3e308fa 100644 > --- a/drivers/hwmon/Kconfig > +++ b/drivers/hwmon/Kconfig > @@ -554,6 +554,14 @@ config SENSORS_IBMPEX > This driver can also be built as a module. If so, the module > will be called ibmpex. > > +config SENSORS_IBMPOWERNV > + tristate "IBM POWERNV platform sensors" > + depends on PPC_POWERNV > + default y > + help > + If you say yes here you get support for the temperature/fan/power > + sensors on your platform. > + > config SENSORS_IIO_HWMON > tristate "Hwmon driver that uses channels specified via iio maps" > depends on IIO > diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile > index c48f987..199c401 100644 > --- a/drivers/hwmon/Makefile > +++ b/drivers/hwmon/Makefile > @@ -71,6 +71,7 @@ obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o > obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o > obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o > obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o > +obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o > obj-$(CONFIG_SENSORS_IIO_HWMON) += iio_hwmon.o > obj-$(CONFIG_SENSORS_INA209) += ina209.o > obj-$(CONFIG_SENSORS_INA2XX) += ina2xx.o > diff --git a/drivers/hwmon/ibmpowernv.c b/drivers/hwmon/ibmpowernv.c > new file mode 100644 > index 0000000..afce620 > --- /dev/null > +++ b/drivers/hwmon/ibmpowernv.c > @@ -0,0 +1,368 @@ > +/* > + * IBM PowerNV platform sensors for temperature/fan/power > + * Copyright (C) 2014 IBM > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License as published by > + * the Free Software Foundation; either version 2 of the License, or > + * (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License > + * along with this program. > + */ > + > +#include <linux/init.h> > +#include <linux/module.h> > +#include <linux/kernel.h> > +#include <linux/hwmon.h> > +#include <linux/hwmon-sysfs.h> > +#include <linux/of.h> > +#include <linux/slab.h> > + > +#include <linux/platform_device.h> > +#include <asm/opal.h> > +#include <linux/err.h> > + > +#define DRVNAME "ibmpowernv" > +#define MAX_ATTR_LEN 32 > + > +/* Sensor suffix name from DT */ > +#define DT_FAULT_ATTR_SUFFIX "faulted" > +#define DT_DATA_ATTR_SUFFIX "data" > +#define DT_THRESHOLD_ATTR_SUFFIX "thrs" > + > +/* > + * Enumerates all the types of sensors in the POWERNV platform and does index > + * into 'struct sensor_group' > + */ > +enum sensors { > + FAN, > + AMBIENT_TEMP, > + POWER_SUPPLY, > + POWER_INPUT, > + MAX_SENSOR_TYPE, > +}; > + > +static struct sensor_group { > + const char *name; > + const char *compatible; > + struct attribute_group group; > + u32 attr_count; > +} sensor_groups[] = { > + {"fan", "ibm,opal-sensor-cooling-fan", {0}, 0}, > + {"temp", "ibm,opal-sensor-amb-temp", {0}, 0}, > + {"in", "ibm,opal-sensor-power-supply", {0}, 0}, > + {"power", "ibm,opal-sensor-power", {0}, 0} > +}; > + > +struct sensor_data { > + u32 id; /* An opaque id of the firmware for each sensor */ > + enum sensors type; > + char name[MAX_ATTR_LEN]; > + struct device_attribute dev_attr; > +}; > + > +struct platform_data { > + const struct attribute_group *attr_groups[MAX_SENSOR_TYPE + 1]; > + u32 sensors_count; /* Total count of sensors from each group */ > +}; > + > +/* Platform device representing all the ibmpowernv sensors */ > +static struct platform_device *pdevice; > + > +static ssize_t show_sensor(struct device *dev, struct device_attribute *devattr, > + char *buf) > +{ > + struct sensor_data *sdata = container_of(devattr, struct sensor_data, > + dev_attr); > + ssize_t ret; > + u32 x; > + > + ret = opal_get_sensor_data(sdata->id, &x); > + if (ret) { > + pr_err("%s: Failed to get opal sensor data\n", __func__); > + return ret; > + } > + > + /* Convert temperature to milli-degrees */ > + if (sdata->type == AMBIENT_TEMP) > + x *= 1000; > + /* Convert power to micro-watts */ > + else if (sdata->type == POWER_INPUT) > + x *= 1000000; > + > + return sprintf(buf, "%d\n", x); > +} > + > +static void __init get_sensor_index_attr(const char *name, u32 *index, char *attr) > +{ > + char *hash_pos = strchr(name, '#'); > + char *dash_pos; > + u32 copy_len; > + char buf[8]; > + > + memset(buf, 0, sizeof(buf)); > + *index = 0; > + *attr = '\0'; > + > + if (hash_pos) { > + dash_pos = strchr(hash_pos, '-'); > + if (dash_pos) { > + copy_len = dash_pos - hash_pos - 1; > + if (copy_len < sizeof(buf)) { > + strncpy(buf, hash_pos + 1, copy_len); > + sscanf(buf, "%d", index); > + } > + > + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); > + } > + } > +} > + > +/* > + * This function translates the DT node name into the 'hwmon' attribute name. > + * IBMPOWERNV device node appear like cooling-fan#2-data, amb-temp#1-thrs etc. > + * which need to be mapped as fan2_input, temp1_max respectively before > + * populating them inside hwmon device class.. > + */ > +static int __init create_hwmon_attr_name(enum sensors type, const char *node_name, > + char *hwmon_attr_name) > +{ > + char attr_suffix[MAX_ATTR_LEN]; > + char *attr_name; > + u32 index; > + > + get_sensor_index_attr(node_name, &index, attr_suffix); > + if (!index || !strlen(attr_suffix)) { > + pr_info("%s: Sensor device node name is invalid, name: %s\n", > + __func__, node_name); > + return -EINVAL; > + } > + > + if (!strcmp(attr_suffix, DT_FAULT_ATTR_SUFFIX)) > + attr_name = "fault"; > + else if(!strcmp(attr_suffix, DT_DATA_ATTR_SUFFIX)) > + attr_name = "input"; > + else if (!strcmp(attr_suffix, DT_THRESHOLD_ATTR_SUFFIX)) { > + if (type == AMBIENT_TEMP) > + attr_name = "max"; > + else if (type == FAN) > + attr_name = "min"; > + else > + return -ENOENT; > + } else > + return -ENOENT; > + > + snprintf(hwmon_attr_name, MAX_ATTR_LEN, "%s%d_%s", > + sensor_groups[type].name, index, attr_name); > + return 0; > +} > + > +static int __init populate_attr_groups(struct platform_device *pdev) > +{ > + struct platform_data *pdata = platform_get_drvdata(pdev); > + const struct attribute_group **pgroups = pdata->attr_groups; > + struct device_node *opal, *np; > + enum sensors type; > + int err = 0; > + > + opal = of_find_node_by_path("/ibm,opal/sensors"); > + if (!opal) { > + pr_err("%s: Opal 'sensors' node not found\n", __func__); > + return -ENODEV; > + } > + > + for_each_child_of_node(opal, np) { > + if (np->name == NULL) > + continue; > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) > + if (of_device_is_compatible(np, > + sensor_groups[type].compatible)) { > + sensor_groups[type].attr_count++; > + break; > + } > + } > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) { > + if (!sensor_groups[type].attr_count) > + continue; > + > + sensor_groups[type].group.attrs = devm_kzalloc(&pdev->dev, > + sizeof(struct attribute*) * > + (sensor_groups[type].attr_count + 1), > + GFP_KERNEL); > + if (!sensor_groups[type].group.attrs) { > + pr_err("%s: Failed to allocate memory for attribute" > + "array\n", __func__); > + err = -ENOMEM; > + goto exit_put_node; > + } > + > + pgroups[type] = &sensor_groups[type].group; > + pdata->sensors_count += sensor_groups[type].attr_count; > + sensor_groups[type].attr_count = 0; > + } > + > +exit_put_node: > + of_node_put(opal); > + return err; > +} > + > +/* > + * Iterate through the device tree for each child of sensor node, create > + * a sysfs attribute file, the file is named by translating the DT node name > + * to the name required by the higher 'hwmon' driver like fan1_input, temp1_max > + * etc.. > + */ > +static int __init create_device_attrs(struct platform_device *pdev) > +{ > + struct platform_data *pdata = platform_get_drvdata(pdev); > + const struct attribute_group **pgroups = pdata->attr_groups; > + struct device_node *opal, *np; > + struct sensor_data *sdata; > + const u32 *sensor_id; > + enum sensors type; > + u32 count = 0; > + int err = 0; > + > + opal = of_find_node_by_path("/ibm,opal/sensors"); > + if (!opal) { > + pr_err("%s: Opal 'sensors' node not found\n", __func__); > + return -ENODEV; > + } > + > + sdata = devm_kzalloc(&pdev->dev, (pdata->sensors_count) * > + sizeof(*sdata), GFP_KERNEL); > + if (!sdata) { > + pr_err("%s: Failed to allocate memory for the sensor_data", > + __func__); > + err = -ENOMEM; > + goto exit_put_node; > + } > + > + for_each_child_of_node(opal, np) { > + if (np->name == NULL) > + continue; > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) > + if (of_device_is_compatible(np, > + sensor_groups[type].compatible)) > + break; > + > + if (type == MAX_SENSOR_TYPE) > + continue; > + > + sensor_id = of_get_property(np, "sensor-id", NULL); > + if (!sensor_id) { > + pr_info("%s: %s doesn't have sensor-id\n", __func__, > + np->name); > + continue; > + } > + > + sdata[count].id = *sensor_id; > + sdata[count].type = type; > + err = create_hwmon_attr_name(type, np->name, sdata[count].name); > + if (err) > + goto exit_put_node; > + > + sysfs_attr_init(&sdata[count].dev_attr.attr); > + sdata[count].dev_attr.attr.name = sdata[count].name; > + sdata[count].dev_attr.attr.mode = S_IRUGO; > + sdata[count].dev_attr.show = show_sensor; > + > + pgroups[type]->attrs[sensor_groups[type].attr_count++] = > + &sdata[count++].dev_attr.attr; > + } > + > +exit_put_node: > + of_node_put(opal); > + return err; > +} > + > +static int __init ibmpowernv_probe(struct platform_device *pdev) > +{ > + struct platform_data *pdata; > + struct device *hwmon_dev; > + int err; > + > + pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); > + if (!pdata) > + return -ENOMEM; > + > + platform_set_drvdata(pdev, pdata); > + pdata->sensors_count = 0; > + err = populate_attr_groups(pdev); > + if (err) > + return err; > + > + /* Create sysfs attribute file for each sensor found in the DT */ > + err = create_device_attrs(pdev); > + if (err) > + return err; > + > + /* Finally, register with hwmon */ > + hwmon_dev = devm_hwmon_device_register_with_groups(&pdev->dev, DRVNAME, > + pdata, > + pdata->attr_groups); > + > + return PTR_ERR_OR_ZERO(hwmon_dev); > +} > + > +static struct platform_driver ibmpowernv_driver = { > + .driver = { > + .owner = THIS_MODULE, > + .name = DRVNAME, > + }, > +}; > + > +static int __init ibmpowernv_init(void) > +{ > + int err; > + > + pdevice = platform_device_alloc(DRVNAME, 0); > + if (!pdevice) { > + pr_err("%s: Device allocation failed\n", __func__); > + err = -ENOMEM; > + goto exit; > + } > + > + err = platform_device_add(pdevice); > + if (err) { > + pr_err("%s: Device addition failed (%d)\n", __func__, err); > + goto exit_device_put; > + } > + > + err = platform_driver_probe(&ibmpowernv_driver, ibmpowernv_probe); > + if (err) { > + pr_err("%s: Platfrom driver probe failed\n", __func__); > + goto exit_device_del; > + } > + > + return 0; > + > +exit_device_del: > + platform_device_del(pdevice); > +exit_device_put: > + platform_device_put(pdevice); > +exit: > + return err; > +} > + > +static void __exit ibmpowernv_exit(void) > +{ > + platform_driver_unregister(&ibmpowernv_driver); > + platform_device_unregister(pdevice); > +} > + > +MODULE_AUTHOR("Neelesh Gupta <neelegup@linux.vnet.ibm.com>"); > +MODULE_DESCRIPTION("IBM POWERNV platform sensors"); > +MODULE_LICENSE("GPL"); > + > +module_init(ibmpowernv_init); > +module_exit(ibmpowernv_exit); > > _______________________________________________ > Linuxppc-dev mailing list > Linuxppc-dev@lists.ozlabs.org > https://lists.ozlabs.org/listinfo/linuxppc-dev [-- Attachment #2: Type: text/html, Size: 15010 bytes --] ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-26 6:34 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-26 6:34 UTC (permalink / raw) To: linuxppc-dev, linux, jdelvare, lm-sensors; +Cc: sbhat QW55IHVwZGF0ZXMgb24gdGhlIHBhdGNoLgoKLSBOZWVsZXNoCgpPbiAwNS8xOS8yMDE0IDA3OjU2 IFBNLCBOZWVsZXNoIEd1cHRhIHdyb3RlOgo+IFRoaXMgcGF0Y2ggYWRkcyBiYXNpYyBrZXJuZWwg ZW5hYmxlbWVudCBmb3IgcmVhZGluZyBwb3dlciB2YWx1ZXMsIGZhbgo+IHNwZWVkIHJwbSBhbmQg dGVtcGVyYXR1cmUgdmFsdWVzIG9uIHBvd2VybnYgcGxhdGZvcm1zIHdoaWNoIHdpbGwKPiBiZSBl eHBvcnRlZCB0byB1c2VyIHNwYWNlIHRocm91Z2ggc3lzZnMgaW50ZXJmYWNlLgo+Cj4gVGVzdCBy ZXN1bHRzOgo+IC0tLS0tLS0tLS0tLS0KPiBbcm9vdEB0dWwxNjNwMSB+XSMgc2Vuc29ycwo+IGli bXBvd2VybnYtaXNhLTAwMDAKPiBBZGFwdGVyOiBJU0EgYWRhcHRlcgo+IGZhbjE6ICAgICAgICA1 NDg3IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IGZhbjI6ICAgICAgICA1MTUyIFJQTSAgKG1pbiA9 ICAgIDAgUlBNKQo+IGZhbjM6ICAgICAgICA1NTkwIFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IGZh bjQ6ICAgICAgICA0OTYzIFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IGZhbjU6ICAgICAgICAgICAw IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IGZhbjY6ICAgICAgICAgICAwIFJQTSAgKG1pbiA9ICAg IDAgUlBNKQo+IGZhbjc6ICAgICAgICA3NDg4IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IGZhbjg6 ICAgICAgICA3OTQ0IFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+IHRlbXAxOiAgICAgICAgKzM5LjDC sEMgIChoaWdoID0gICswLjDCsEMpCj4gcG93ZXIxOiAgICAgIDE5Mi4wMCBXCj4KPiBbcm9vdEB0 dWwxNjNwMSB+XSMgbHMgL3N5cy9kZXZpY2VzL3BsYXRmb3JtLwo+IGFsYXJtdGltZXIgIGlibXBv d2VybnYuMCAgcnRjLWdlbmVyaWMgIHNlcmlhbDgyNTAgIHVldmVudAo+IFtyb290QHR1bDE2M3Ax IH5dIyBscyAvc3lzL2RldmljZXMvcGxhdGZvcm0vaWJtcG93ZXJudi4wLwo+IGRyaXZlci8gICAg aHdtb24vICAgICBtb2RhbGlhcyAgIHN1YnN5c3RlbS8gdWV2ZW50Cj4gW3Jvb3RAdHVsMTYzcDEg fl0jIGxzIC9zeXMvZGV2aWNlcy9wbGF0Zm9ybS9pYm1wb3dlcm52LjAvaHdtb24vaHdtb24wLwo+ IGRldmljZQkgICAgZmFuMl9taW4JZmFuNF9taW4gICAgZmFuNl9taW4JZmFuOF9taW4gICBwb3dl cjFfaW5wdXQKPiBmYW4xX2ZhdWx0ICBmYW4zX2ZhdWx0CWZhbjVfZmF1bHQgIGZhbjdfZmF1bHQJ aW4xX2ZhdWx0ICBzdWJzeXN0ZW0KPiBmYW4xX2lucHV0ICBmYW4zX2lucHV0CWZhbjVfaW5wdXQg IGZhbjdfaW5wdXQJaW4yX2ZhdWx0ICB0ZW1wMV9pbnB1dAo+IGZhbjFfbWluICAgIGZhbjNfbWlu CWZhbjVfbWluICAgIGZhbjdfbWluCWluM19mYXVsdCAgdGVtcDFfbWF4Cj4gZmFuMl9mYXVsdCAg ZmFuNF9mYXVsdAlmYW42X2ZhdWx0ICBmYW44X2ZhdWx0CWluNF9mYXVsdCAgdWV2ZW50Cj4gZmFu Ml9pbnB1dCAgZmFuNF9pbnB1dAlmYW42X2lucHV0ICBmYW44X2lucHV0CW5hbWUKPiBbcm9vdEB0 dWwxNjNwMSB+XSMKPiBbcm9vdEB0dWwxNjNwMSB+XSMgbHMgL3N5cy9jbGFzcy9od21vbi9od21v bjAvCj4gZGV2aWNlCSAgICBmYW4yX21pbglmYW40X21pbiAgICBmYW42X21pbglmYW44X21pbiAg IHBvd2VyMV9pbnB1dAo+IGZhbjFfZmF1bHQgIGZhbjNfZmF1bHQJZmFuNV9mYXVsdCAgZmFuN19m YXVsdAlpbjFfZmF1bHQgIHN1YnN5c3RlbQo+IGZhbjFfaW5wdXQgIGZhbjNfaW5wdXQJZmFuNV9p bnB1dCAgZmFuN19pbnB1dAlpbjJfZmF1bHQgIHRlbXAxX2lucHV0Cj4gZmFuMV9taW4gICAgZmFu M19taW4JZmFuNV9taW4gICAgZmFuN19taW4JaW4zX2ZhdWx0ICB0ZW1wMV9tYXgKPiBmYW4yX2Zh dWx0ICBmYW40X2ZhdWx0CWZhbjZfZmF1bHQgIGZhbjhfZmF1bHQJaW40X2ZhdWx0ICB1ZXZlbnQK PiBmYW4yX2lucHV0ICBmYW40X2lucHV0CWZhbjZfaW5wdXQgIGZhbjhfaW5wdXQJbmFtZQo+IFty b290QHR1bDE2M3AxIH5dIwo+Cj4gU2lnbmVkLW9mZi1ieTogTmVlbGVzaCBHdXB0YSA8bmVlbGVn dXBAbGludXgudm5ldC5pYm0uY29tPgo+IC0tLQo+Cj4gQ2hhbmdlcyBpbiB2Mgo+ID09PT09PT09 PT09PT0KPiAtIEdlbmVyaWMgdXNlIG9mIGRldm1fKiBmdW5jdGlvbnMgaW4gaHdtb24gbGlrZSB1 c2luZyBkZXZtX2t6YWxsb2MoKSBmb3IgZHluYW1pYwo+ICAgIG1lbW9yeSByZXF1ZXN0LCBhdm9p ZGluZyB0aGUgbmVlZCB0byBleHBsaWNpdCBmcmVlIG9mIG1lbW9yeS4KPiAgICBBZGRpbmcgJ3N0 cnVjdCBhdHRyaWJ1dGVfZ3JvdXAnIGFzIG1lbWJlciBvZiBwbGF0Zm9ybSBkYXRhIHN0cnVjdHVy ZSB0byBiZQo+ICAgIHBvcHVsYXRlZCBhbmQgdGhlbiBwYXNzZWQgdG8gZGV2bV9od21vbl9kZXZp Y2VfcmVnaXN0ZXJfd2l0aF9ncm91cHMoKS4KPgo+ICAgIE5vdGU6IEhhdmluZyBhbiBhcnJheSBv ZiBwb2ludGVycyBvZiAnYXR0cmlidXRlX2dyb3VwJyBhbmQgZWFjaCBncm91cAo+ICAgIGNvcnJl c3BvbmRzIHRvICdlbnVtIHNlbnNvcnMnIHR5cGUuIE5vdCBjb21wbGV0ZWx5IHN1cmUsIGlmIGl0 J3MgaWRlYWwgb3IKPiAgICBjb3VsZCBoYXZlIGp1c3Qgb25lIGdyb3VwIHBvcHVsYXRlZCB3aXRo IGF0dHJpYnV0ZXMgb2Ygc2Vuc29yIHR5cGVzPwo+Cj4gLSAnaWJtcG93ZXJudicgaXMgbm90IGhv dC1wbHVnZ2FibGUgZGV2aWNlIHNvIG1vdmluZyAncGxhdGZvcm1fZHJpdmVyJyBjYWxsYmFjawo+ ICAgIGZ1bmN0aW9uIChwcm9iZSkgYXMgcGFydCBvZiBfX2luaXQgY29kZS4KPiAtIEZpeGVkIGlz c3VlcyByZWxhdGVkIHRvIGNvZGluZyBzdHlsZS4KPiAtIE90aGVyIGdlbmVyYWwgY29tbWVudHMg aW4gdjEuCj4KPiAgIGRyaXZlcnMvaHdtb24vS2NvbmZpZyAgICAgIHwgICAgOCArCj4gICBkcml2 ZXJzL2h3bW9uL01ha2VmaWxlICAgICB8ICAgIDEKPiAgIGRyaXZlcnMvaHdtb24vaWJtcG93ZXJu di5jIHwgIDM2OCArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwo+ ICAgMyBmaWxlcyBjaGFuZ2VkLCAzNzcgaW5zZXJ0aW9ucygrKQo+ICAgY3JlYXRlIG1vZGUgMTAw NjQ0IGRyaXZlcnMvaHdtb24vaWJtcG93ZXJudi5jCj4KPiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9o d21vbi9LY29uZmlnIGIvZHJpdmVycy9od21vbi9LY29uZmlnCj4gaW5kZXggYmMxOTZmNC4uM2Uz MDhmYSAxMDA2NDQKPiAtLS0gYS9kcml2ZXJzL2h3bW9uL0tjb25maWcKPiArKysgYi9kcml2ZXJz L2h3bW9uL0tjb25maWcKPiBAQCAtNTU0LDYgKzU1NCwxNCBAQCBjb25maWcgU0VOU09SU19JQk1Q RVgKPiAgIAkgIFRoaXMgZHJpdmVyIGNhbiBhbHNvIGJlIGJ1aWx0IGFzIGEgbW9kdWxlLiAgSWYg c28sIHRoZSBtb2R1bGUKPiAgIAkgIHdpbGwgYmUgY2FsbGVkIGlibXBleC4KPiAgIAo+ICtjb25m aWcgU0VOU09SU19JQk1QT1dFUk5WCj4gKwl0cmlzdGF0ZSAiSUJNIFBPV0VSTlYgcGxhdGZvcm0g c2Vuc29ycyIKPiArCWRlcGVuZHMgb24gUFBDX1BPV0VSTlYKPiArCWRlZmF1bHQgeQo+ICsJaGVs cAo+ICsJICBJZiB5b3Ugc2F5IHllcyBoZXJlIHlvdSBnZXQgc3VwcG9ydCBmb3IgdGhlIHRlbXBl cmF0dXJlL2Zhbi9wb3dlcgo+ICsJICBzZW5zb3JzIG9uIHlvdXIgcGxhdGZvcm0uCj4gKwo+ICAg Y29uZmlnIFNFTlNPUlNfSUlPX0hXTU9OCj4gICAJdHJpc3RhdGUgIkh3bW9uIGRyaXZlciB0aGF0 IHVzZXMgY2hhbm5lbHMgc3BlY2lmaWVkIHZpYSBpaW8gbWFwcyIKPiAgIAlkZXBlbmRzIG9uIElJ Two+IGRpZmYgLS1naXQgYS9kcml2ZXJzL2h3bW9uL01ha2VmaWxlIGIvZHJpdmVycy9od21vbi9N YWtlZmlsZQo+IGluZGV4IGM0OGY5ODcuLjE5OWM0MDEgMTAwNjQ0Cj4gLS0tIGEvZHJpdmVycy9o d21vbi9NYWtlZmlsZQo+ICsrKyBiL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUKPiBAQCAtNzEsNiAr NzEsNyBAQCBvYmotJChDT05GSUdfU0VOU09SU19VTFRSQTQ1KQkrPSB1bHRyYTQ1X2Vudi5vCj4g ICBvYmotJChDT05GSUdfU0VOU09SU19JNUtfQU1CKQkrPSBpNWtfYW1iLm8KPiAgIG9iai0kKENP TkZJR19TRU5TT1JTX0lCTUFFTSkJKz0gaWJtYWVtLm8KPiAgIG9iai0kKENPTkZJR19TRU5TT1JT X0lCTVBFWCkJKz0gaWJtcGV4Lm8KPiArb2JqLSQoQ09ORklHX1NFTlNPUlNfSUJNUE9XRVJOVikr PSBpYm1wb3dlcm52Lm8KPiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0lJT19IV01PTikgKz0gaWlv X2h3bW9uLm8KPiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0lOQTIwOSkJKz0gaW5hMjA5Lm8KPiAg IG9iai0kKENPTkZJR19TRU5TT1JTX0lOQTJYWCkJKz0gaW5hMnh4Lm8KPiBkaWZmIC0tZ2l0IGEv ZHJpdmVycy9od21vbi9pYm1wb3dlcm52LmMgYi9kcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwo+ IG5ldyBmaWxlIG1vZGUgMTAwNjQ0Cj4gaW5kZXggMDAwMDAwMC4uYWZjZTYyMAo+IC0tLSAvZGV2 L251bGwKPiArKysgYi9kcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwo+IEBAIC0wLDAgKzEsMzY4 IEBACj4gKy8qCj4gKyAqIElCTSBQb3dlck5WIHBsYXRmb3JtIHNlbnNvcnMgZm9yIHRlbXBlcmF0 dXJlL2Zhbi9wb3dlcgo+ICsgKiBDb3B5cmlnaHQgKEMpIDIwMTQgSUJNCj4gKyAqCj4gKyAqIFRo aXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQv b3IgbW9kaWZ5Cj4gKyAqIGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVi bGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5Cj4gKyAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5k YXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCj4gKyAqIChhdCB5b3Vy IG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCj4gKyAqCj4gKyAqIFRoaXMgcHJvZ3JhbSBpcyBk aXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAo+ICsgKiBidXQg V0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBv Zgo+ICsgKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBP U0UuICBTZWUgdGhlCj4gKyAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRl dGFpbHMuCj4gKyAqCj4gKyAqIFlvdSBzaG91bGQgaGF2ZSByZWNlaXZlZCBhIGNvcHkgb2YgdGhl IEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlCj4gKyAqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFt Lgo+ICsgKi8KPiArCj4gKyNpbmNsdWRlIDxsaW51eC9pbml0Lmg+Cj4gKyNpbmNsdWRlIDxsaW51 eC9tb2R1bGUuaD4KPiArI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgo+ICsjaW5jbHVkZSA8bGlu dXgvaHdtb24uaD4KPiArI2luY2x1ZGUgPGxpbnV4L2h3bW9uLXN5c2ZzLmg+Cj4gKyNpbmNsdWRl IDxsaW51eC9vZi5oPgo+ICsjaW5jbHVkZSA8bGludXgvc2xhYi5oPgo+ICsKPiArI2luY2x1ZGUg PGxpbnV4L3BsYXRmb3JtX2RldmljZS5oPgo+ICsjaW5jbHVkZSA8YXNtL29wYWwuaD4KPiArI2lu Y2x1ZGUgPGxpbnV4L2Vyci5oPgo+ICsKPiArI2RlZmluZSBEUlZOQU1FCQkiaWJtcG93ZXJudiIK PiArI2RlZmluZSBNQVhfQVRUUl9MRU4JMzIKPiArCj4gKy8qIFNlbnNvciBzdWZmaXggbmFtZSBm cm9tIERUICovCj4gKyNkZWZpbmUgRFRfRkFVTFRfQVRUUl9TVUZGSVgJCSJmYXVsdGVkIgo+ICsj ZGVmaW5lIERUX0RBVEFfQVRUUl9TVUZGSVgJCSJkYXRhIgo+ICsjZGVmaW5lIERUX1RIUkVTSE9M RF9BVFRSX1NVRkZJWAkidGhycyIKPiArCj4gKy8qCj4gKyAqIEVudW1lcmF0ZXMgYWxsIHRoZSB0 eXBlcyBvZiBzZW5zb3JzIGluIHRoZSBQT1dFUk5WIHBsYXRmb3JtIGFuZCBkb2VzIGluZGV4Cj4g KyAqIGludG8gJ3N0cnVjdCBzZW5zb3JfZ3JvdXAnCj4gKyAqLwo+ICtlbnVtIHNlbnNvcnMgewo+ ICsJRkFOLAo+ICsJQU1CSUVOVF9URU1QLAo+ICsJUE9XRVJfU1VQUExZLAo+ICsJUE9XRVJfSU5Q VVQsCj4gKwlNQVhfU0VOU09SX1RZUEUsCj4gK307Cj4gKwo+ICtzdGF0aWMgc3RydWN0IHNlbnNv cl9ncm91cCB7Cj4gKwljb25zdCBjaGFyICpuYW1lOwo+ICsJY29uc3QgY2hhciAqY29tcGF0aWJs ZTsKPiArCXN0cnVjdCBhdHRyaWJ1dGVfZ3JvdXAgZ3JvdXA7Cj4gKwl1MzIgYXR0cl9jb3VudDsK PiArfSBzZW5zb3JfZ3JvdXBzW10gPSB7Cj4gKwl7ImZhbiIsICJpYm0sb3BhbC1zZW5zb3ItY29v bGluZy1mYW4iLCB7MH0sIDB9LAo+ICsJeyJ0ZW1wIiwgImlibSxvcGFsLXNlbnNvci1hbWItdGVt cCIsIHswfSwgMH0sCj4gKwl7ImluIiwgImlibSxvcGFsLXNlbnNvci1wb3dlci1zdXBwbHkiLCB7 MH0sIDB9LAo+ICsJeyJwb3dlciIsICJpYm0sb3BhbC1zZW5zb3ItcG93ZXIiLCB7MH0sIDB9Cj4g K307Cj4gKwo+ICtzdHJ1Y3Qgc2Vuc29yX2RhdGEgewo+ICsJdTMyIGlkOyAvKiBBbiBvcGFxdWUg aWQgb2YgdGhlIGZpcm13YXJlIGZvciBlYWNoIHNlbnNvciAqLwo+ICsJZW51bSBzZW5zb3JzIHR5 cGU7Cj4gKwljaGFyIG5hbWVbTUFYX0FUVFJfTEVOXTsKPiArCXN0cnVjdCBkZXZpY2VfYXR0cmli dXRlIGRldl9hdHRyOwo+ICt9Owo+ICsKPiArc3RydWN0IHBsYXRmb3JtX2RhdGEgewo+ICsJY29u c3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqYXR0cl9ncm91cHNbTUFYX1NFTlNPUl9UWVBFICsg MV07Cj4gKwl1MzIgc2Vuc29yc19jb3VudDsgLyogVG90YWwgY291bnQgb2Ygc2Vuc29ycyBmcm9t IGVhY2ggZ3JvdXAgKi8KPiArfTsKPiArCj4gKy8qIFBsYXRmb3JtIGRldmljZSByZXByZXNlbnRp bmcgYWxsIHRoZSBpYm1wb3dlcm52IHNlbnNvcnMgKi8KPiArc3RhdGljIHN0cnVjdCBwbGF0Zm9y bV9kZXZpY2UgKnBkZXZpY2U7Cj4gKwo+ICtzdGF0aWMgc3NpemVfdCBzaG93X3NlbnNvcihzdHJ1 Y3QgZGV2aWNlICpkZXYsIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICpkZXZhdHRyLAo+ICsJCQkg ICBjaGFyICpidWYpCj4gK3sKPiArCXN0cnVjdCBzZW5zb3JfZGF0YSAqc2RhdGEgPSBjb250YWlu ZXJfb2YoZGV2YXR0ciwgc3RydWN0IHNlbnNvcl9kYXRhLAo+ICsJCQkJCQkgZGV2X2F0dHIpOwo+ ICsJc3NpemVfdCByZXQ7Cj4gKwl1MzIgeDsKPiArCj4gKwlyZXQgPSBvcGFsX2dldF9zZW5zb3Jf ZGF0YShzZGF0YS0+aWQsICZ4KTsKPiArCWlmIChyZXQpIHsKPiArCQlwcl9lcnIoIiVzOiBGYWls ZWQgdG8gZ2V0IG9wYWwgc2Vuc29yIGRhdGFcbiIsIF9fZnVuY19fKTsKPiArCQlyZXR1cm4gcmV0 Owo+ICsJfQo+ICsKPiArCS8qIENvbnZlcnQgdGVtcGVyYXR1cmUgdG8gbWlsbGktZGVncmVlcyAq Lwo+ICsJaWYgKHNkYXRhLT50eXBlID09IEFNQklFTlRfVEVNUCkKPiArCQl4ICo9IDEwMDA7Cj4g KwkvKiBDb252ZXJ0IHBvd2VyIHRvIG1pY3JvLXdhdHRzICovCj4gKwllbHNlIGlmIChzZGF0YS0+ dHlwZSA9PSBQT1dFUl9JTlBVVCkKPiArCQl4ICo9IDEwMDAwMDA7Cj4gKwo+ICsJcmV0dXJuIHNw cmludGYoYnVmLCAiJWRcbiIsIHgpOwo+ICt9Cj4gKwo+ICtzdGF0aWMgdm9pZCBfX2luaXQgZ2V0 X3NlbnNvcl9pbmRleF9hdHRyKGNvbnN0IGNoYXIgKm5hbWUsIHUzMiAqaW5kZXgsIGNoYXIgKmF0 dHIpCj4gK3sKPiArCWNoYXIgKmhhc2hfcG9zID0gc3RyY2hyKG5hbWUsICcjJyk7Cj4gKwljaGFy ICpkYXNoX3BvczsKPiArCXUzMiBjb3B5X2xlbjsKPiArCWNoYXIgYnVmWzhdOwo+ICsKPiArCW1l bXNldChidWYsIDAsIHNpemVvZihidWYpKTsKPiArCSppbmRleCA9IDA7Cj4gKwkqYXR0ciA9ICdc MCc7Cj4gKwo+ICsJaWYgKGhhc2hfcG9zKSB7Cj4gKwkJZGFzaF9wb3MgPSBzdHJjaHIoaGFzaF9w b3MsICctJyk7Cj4gKwkJaWYgKGRhc2hfcG9zKSB7Cj4gKwkJCWNvcHlfbGVuID0gZGFzaF9wb3Mg LSBoYXNoX3BvcyAtIDE7Cj4gKwkJCWlmIChjb3B5X2xlbiA8IHNpemVvZihidWYpKSB7Cj4gKwkJ CQlzdHJuY3B5KGJ1ZiwgaGFzaF9wb3MgKyAxLCBjb3B5X2xlbik7Cj4gKwkJCQlzc2NhbmYoYnVm LCAiJWQiLCBpbmRleCk7Cj4gKwkJCX0KPiArCj4gKwkJCXN0cm5jcHkoYXR0ciwgZGFzaF9wb3Mg KyAxLCBNQVhfQVRUUl9MRU4pOwo+ICsJCX0KPiArCX0KPiArfQo+ICsKPiArLyoKPiArICogVGhp cyBmdW5jdGlvbiB0cmFuc2xhdGVzIHRoZSBEVCBub2RlIG5hbWUgaW50byB0aGUgJ2h3bW9uJyBh dHRyaWJ1dGUgbmFtZS4KPiArICogSUJNUE9XRVJOViBkZXZpY2Ugbm9kZSBhcHBlYXIgbGlrZSBj b29saW5nLWZhbiMyLWRhdGEsIGFtYi10ZW1wIzEtdGhycyBldGMuCj4gKyAqIHdoaWNoIG5lZWQg dG8gYmUgbWFwcGVkIGFzIGZhbjJfaW5wdXQsIHRlbXAxX21heCByZXNwZWN0aXZlbHkgYmVmb3Jl Cj4gKyAqIHBvcHVsYXRpbmcgdGhlbSBpbnNpZGUgaHdtb24gZGV2aWNlIGNsYXNzLi4KPiArICov Cj4gK3N0YXRpYyBpbnQgX19pbml0IGNyZWF0ZV9od21vbl9hdHRyX25hbWUoZW51bSBzZW5zb3Jz IHR5cGUsIGNvbnN0IGNoYXIgKm5vZGVfbmFtZSwKPiArCQkJCSAgY2hhciAqaHdtb25fYXR0cl9u YW1lKQo+ICt7Cj4gKwljaGFyIGF0dHJfc3VmZml4W01BWF9BVFRSX0xFTl07Cj4gKwljaGFyICph dHRyX25hbWU7Cj4gKwl1MzIgaW5kZXg7Cj4gKwo+ICsJZ2V0X3NlbnNvcl9pbmRleF9hdHRyKG5v ZGVfbmFtZSwgJmluZGV4LCBhdHRyX3N1ZmZpeCk7Cj4gKwlpZiAoIWluZGV4IHx8ICFzdHJsZW4o YXR0cl9zdWZmaXgpKSB7Cj4gKwkJcHJfaW5mbygiJXM6IFNlbnNvciBkZXZpY2Ugbm9kZSBuYW1l IGlzIGludmFsaWQsIG5hbWU6ICVzXG4iLAo+ICsJCQkJX19mdW5jX18sIG5vZGVfbmFtZSk7Cj4g KwkJcmV0dXJuIC1FSU5WQUw7Cj4gKwl9Cj4gKwo+ICsJaWYgKCFzdHJjbXAoYXR0cl9zdWZmaXgs IERUX0ZBVUxUX0FUVFJfU1VGRklYKSkKPiArCQlhdHRyX25hbWUgPSAiZmF1bHQiOwo+ICsJZWxz ZSBpZighc3RyY21wKGF0dHJfc3VmZml4LCBEVF9EQVRBX0FUVFJfU1VGRklYKSkKPiArCQlhdHRy X25hbWUgPSAiaW5wdXQiOwo+ICsJZWxzZSBpZiAoIXN0cmNtcChhdHRyX3N1ZmZpeCwgRFRfVEhS RVNIT0xEX0FUVFJfU1VGRklYKSkgewo+ICsJCWlmICh0eXBlID09IEFNQklFTlRfVEVNUCkKPiAr CQkJYXR0cl9uYW1lID0gIm1heCI7Cj4gKwkJZWxzZSBpZiAodHlwZSA9PSBGQU4pCj4gKwkJCWF0 dHJfbmFtZSA9ICJtaW4iOwo+ICsJCWVsc2UKPiArCQkJcmV0dXJuIC1FTk9FTlQ7Cj4gKwl9IGVs c2UKPiArCQlyZXR1cm4gLUVOT0VOVDsKPiArCj4gKwlzbnByaW50Zihod21vbl9hdHRyX25hbWUs IE1BWF9BVFRSX0xFTiwgIiVzJWRfJXMiLAo+ICsJCQlzZW5zb3JfZ3JvdXBzW3R5cGVdLm5hbWUs IGluZGV4LCBhdHRyX25hbWUpOwo+ICsJcmV0dXJuIDA7Cj4gK30KPiArCj4gK3N0YXRpYyBpbnQg X19pbml0IHBvcHVsYXRlX2F0dHJfZ3JvdXBzKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYp Cj4gK3sKPiArCXN0cnVjdCBwbGF0Zm9ybV9kYXRhICpwZGF0YSA9IHBsYXRmb3JtX2dldF9kcnZk YXRhKHBkZXYpOwo+ICsJY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqKnBncm91cHMgPSBw ZGF0YS0+YXR0cl9ncm91cHM7Cj4gKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpucDsKPiAr CWVudW0gc2Vuc29ycyB0eXBlOwo+ICsJaW50IGVyciA9IDA7Cj4gKwo+ICsJb3BhbCA9IG9mX2Zp bmRfbm9kZV9ieV9wYXRoKCIvaWJtLG9wYWwvc2Vuc29ycyIpOwo+ICsgICAgICAgIGlmICghb3Bh bCkgewo+ICsJCXByX2VycigiJXM6IE9wYWwgJ3NlbnNvcnMnIG5vZGUgbm90IGZvdW5kXG4iLCBf X2Z1bmNfXyk7Cj4gKwkJcmV0dXJuIC1FTk9ERVY7Cj4gKyAgICAgICAgfQo+ICsKPiArCWZvcl9l YWNoX2NoaWxkX29mX25vZGUob3BhbCwgbnApIHsKPiArCQlpZiAobnAtPm5hbWUgPT0gTlVMTCkK PiArCQkJY29udGludWU7Cj4gKwo+ICsJCWZvciAodHlwZSA9IDA7IHR5cGUgPCBNQVhfU0VOU09S X1RZUEU7IHR5cGUrKykKPiArCQkJaWYgKG9mX2RldmljZV9pc19jb21wYXRpYmxlKG5wLAo+ICsJ CQkJc2Vuc29yX2dyb3Vwc1t0eXBlXS5jb21wYXRpYmxlKSkgewo+ICsJCQkJc2Vuc29yX2dyb3Vw c1t0eXBlXS5hdHRyX2NvdW50Kys7Cj4gKwkJCQlicmVhazsKPiArCQkJfQo+ICsJfQo+ICsKPiAr CWZvciAodHlwZSA9IDA7IHR5cGUgPCBNQVhfU0VOU09SX1RZUEU7IHR5cGUrKykgewo+ICsJCWlm ICghc2Vuc29yX2dyb3Vwc1t0eXBlXS5hdHRyX2NvdW50KQo+ICsJCQljb250aW51ZTsKPiArCj4g KwkJc2Vuc29yX2dyb3Vwc1t0eXBlXS5ncm91cC5hdHRycyA9IGRldm1fa3phbGxvYygmcGRldi0+ ZGV2LAo+ICsJCQkJCXNpemVvZihzdHJ1Y3QgYXR0cmlidXRlKikgKgo+ICsJCQkJCShzZW5zb3Jf Z3JvdXBzW3R5cGVdLmF0dHJfY291bnQgKyAxKSwKPiArCQkJCQlHRlBfS0VSTkVMKTsKPiArCQlp ZiAoIXNlbnNvcl9ncm91cHNbdHlwZV0uZ3JvdXAuYXR0cnMpIHsKPiArCQkJcHJfZXJyKCIlczog RmFpbGVkIHRvIGFsbG9jYXRlIG1lbW9yeSBmb3IgYXR0cmlidXRlIgo+ICsJCQkJCSJhcnJheVxu IiwgX19mdW5jX18pOwo+ICsJCQllcnIgPSAtRU5PTUVNOwo+ICsJCQlnb3RvIGV4aXRfcHV0X25v ZGU7Cj4gKwkJfQo+ICsKPiArCQlwZ3JvdXBzW3R5cGVdID0gJnNlbnNvcl9ncm91cHNbdHlwZV0u Z3JvdXA7Cj4gKwkJcGRhdGEtPnNlbnNvcnNfY291bnQgKz0gc2Vuc29yX2dyb3Vwc1t0eXBlXS5h dHRyX2NvdW50Owo+ICsJCXNlbnNvcl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCA9IDA7Cj4gKwl9 Cj4gKwo+ICtleGl0X3B1dF9ub2RlOgo+ICsJb2Zfbm9kZV9wdXQob3BhbCk7Cj4gKwlyZXR1cm4g ZXJyOwo+ICt9Cj4gKwo+ICsvKgo+ICsgKiBJdGVyYXRlIHRocm91Z2ggdGhlIGRldmljZSB0cmVl IGZvciBlYWNoIGNoaWxkIG9mIHNlbnNvciBub2RlLCBjcmVhdGUKPiArICogYSBzeXNmcyBhdHRy aWJ1dGUgZmlsZSwgdGhlIGZpbGUgaXMgbmFtZWQgYnkgdHJhbnNsYXRpbmcgdGhlIERUIG5vZGUg bmFtZQo+ICsgKiB0byB0aGUgbmFtZSByZXF1aXJlZCBieSB0aGUgaGlnaGVyICdod21vbicgZHJp dmVyIGxpa2UgZmFuMV9pbnB1dCwgdGVtcDFfbWF4Cj4gKyAqIGV0Yy4uCj4gKyAqLwo+ICtzdGF0 aWMgaW50IF9faW5pdCBjcmVhdGVfZGV2aWNlX2F0dHJzKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2Ug KnBkZXYpCj4gK3sKPiArCXN0cnVjdCBwbGF0Zm9ybV9kYXRhICpwZGF0YSA9IHBsYXRmb3JtX2dl dF9kcnZkYXRhKHBkZXYpOwo+ICsJY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqKnBncm91 cHMgPSBwZGF0YS0+YXR0cl9ncm91cHM7Cj4gKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpu cDsKPiArCXN0cnVjdCBzZW5zb3JfZGF0YSAqc2RhdGE7Cj4gKwljb25zdCB1MzIgKnNlbnNvcl9p ZDsKPiArCWVudW0gc2Vuc29ycyB0eXBlOwo+ICsJdTMyIGNvdW50ID0gMDsKPiArCWludCBlcnIg PSAwOwo+ICsKPiArCW9wYWwgPSBvZl9maW5kX25vZGVfYnlfcGF0aCgiL2libSxvcGFsL3NlbnNv cnMiKTsKPiArICAgICAgICBpZiAoIW9wYWwpIHsKPiArCQlwcl9lcnIoIiVzOiBPcGFsICdzZW5z b3JzJyBub2RlIG5vdCBmb3VuZFxuIiwgX19mdW5jX18pOwo+ICsJCXJldHVybiAtRU5PREVWOwo+ ICsgICAgICAgIH0KPiArCj4gKwlzZGF0YSA9IGRldm1fa3phbGxvYygmcGRldi0+ZGV2LCAocGRh dGEtPnNlbnNvcnNfY291bnQpICoKPiArCQkJICAgICBzaXplb2YoKnNkYXRhKSwgR0ZQX0tFUk5F TCk7Cj4gKwlpZiAoIXNkYXRhKSB7Cj4gKwkJcHJfZXJyKCIlczogRmFpbGVkIHRvIGFsbG9jYXRl IG1lbW9yeSBmb3IgdGhlIHNlbnNvcl9kYXRhIiwKPiArCQkJCV9fZnVuY19fKTsKPiArCQllcnIg PSAtRU5PTUVNOwo+ICsJCWdvdG8gZXhpdF9wdXRfbm9kZTsKPiArCX0KPiArCj4gKwlmb3JfZWFj aF9jaGlsZF9vZl9ub2RlKG9wYWwsIG5wKSB7Cj4gKyAgICAgICAgICAgICAgICBpZiAobnAtPm5h bWUgPT0gTlVMTCkKPiArICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7Cj4gKwo+ICsJ CWZvciAodHlwZSA9IDA7IHR5cGUgPCBNQVhfU0VOU09SX1RZUEU7IHR5cGUrKykKPiArCQkJaWYg KG9mX2RldmljZV9pc19jb21wYXRpYmxlKG5wLAo+ICsJCQkJCXNlbnNvcl9ncm91cHNbdHlwZV0u Y29tcGF0aWJsZSkpCj4gKwkJCQlicmVhazsKPiArCj4gKwkJaWYgKHR5cGUgPT0gTUFYX1NFTlNP Ul9UWVBFKQo+ICsJCQljb250aW51ZTsKPiArCj4gKwkJc2Vuc29yX2lkID0gb2ZfZ2V0X3Byb3Bl cnR5KG5wLCAic2Vuc29yLWlkIiwgTlVMTCk7Cj4gKwkJaWYgKCFzZW5zb3JfaWQpIHsKPiArCQkJ cHJfaW5mbygiJXM6ICVzIGRvZXNuJ3QgaGF2ZSBzZW5zb3ItaWRcbiIsIF9fZnVuY19fLAo+ICsJ CQkJbnAtPm5hbWUpOwo+ICsJCQljb250aW51ZTsKPiArCQl9Cj4gKwo+ICsJCXNkYXRhW2NvdW50 XS5pZCA9ICpzZW5zb3JfaWQ7Cj4gKwkJc2RhdGFbY291bnRdLnR5cGUgPSB0eXBlOwo+ICsJCWVy ciA9IGNyZWF0ZV9od21vbl9hdHRyX25hbWUodHlwZSwgbnAtPm5hbWUsIHNkYXRhW2NvdW50XS5u YW1lKTsKPiArCQlpZiAoZXJyKQo+ICsJCQlnb3RvIGV4aXRfcHV0X25vZGU7Cj4gKwo+ICsJCXN5 c2ZzX2F0dHJfaW5pdCgmc2RhdGFbY291bnRdLmRldl9hdHRyLmF0dHIpOwo+ICsJCXNkYXRhW2Nv dW50XS5kZXZfYXR0ci5hdHRyLm5hbWUgPSBzZGF0YVtjb3VudF0ubmFtZTsKPiArCQlzZGF0YVtj b3VudF0uZGV2X2F0dHIuYXR0ci5tb2RlID0gU19JUlVHTzsKPiArCQlzZGF0YVtjb3VudF0uZGV2 X2F0dHIuc2hvdyA9IHNob3dfc2Vuc29yOwo+ICsKPiArCQlwZ3JvdXBzW3R5cGVdLT5hdHRyc1tz ZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQrK10gPQo+ICsJCQkJJnNkYXRhW2NvdW50Kytd LmRldl9hdHRyLmF0dHI7Cj4gKwl9Cj4gKwo+ICtleGl0X3B1dF9ub2RlOgo+ICsJb2Zfbm9kZV9w dXQob3BhbCk7Cj4gKwlyZXR1cm4gZXJyOwo+ICt9Cj4gKwo+ICtzdGF0aWMgaW50IF9faW5pdCBp Ym1wb3dlcm52X3Byb2JlKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYpCj4gK3sKPiArCXN0 cnVjdCBwbGF0Zm9ybV9kYXRhICpwZGF0YTsKPiArCXN0cnVjdCBkZXZpY2UgKmh3bW9uX2RldjsK PiArCWludCBlcnI7Cj4gKwo+ICsJcGRhdGEgPSBkZXZtX2t6YWxsb2MoJnBkZXYtPmRldiwgc2l6 ZW9mKCpwZGF0YSksIEdGUF9LRVJORUwpOwo+ICsJaWYgKCFwZGF0YSkKPiArCQlyZXR1cm4gLUVO T01FTTsKPiArCj4gKwlwbGF0Zm9ybV9zZXRfZHJ2ZGF0YShwZGV2LCBwZGF0YSk7Cj4gKwlwZGF0 YS0+c2Vuc29yc19jb3VudCA9IDA7Cj4gKwllcnIgPSBwb3B1bGF0ZV9hdHRyX2dyb3VwcyhwZGV2 KTsKPiArCWlmIChlcnIpCj4gKwkJcmV0dXJuIGVycjsKPiArCj4gKwkvKiBDcmVhdGUgc3lzZnMg YXR0cmlidXRlIGZpbGUgZm9yIGVhY2ggc2Vuc29yIGZvdW5kIGluIHRoZSBEVCAqLwo+ICsJZXJy ID0gY3JlYXRlX2RldmljZV9hdHRycyhwZGV2KTsKPiArCWlmIChlcnIpCj4gKwkJcmV0dXJuIGVy cjsKPiArCj4gKwkvKiBGaW5hbGx5LCByZWdpc3RlciB3aXRoIGh3bW9uICovCj4gKwlod21vbl9k ZXYgPSBkZXZtX2h3bW9uX2RldmljZV9yZWdpc3Rlcl93aXRoX2dyb3VwcygmcGRldi0+ZGV2LCBE UlZOQU1FLAo+ICsJCQkJCQkJICAgcGRhdGEsCj4gKwkJCQkJCQkgICBwZGF0YS0+YXR0cl9ncm91 cHMpOwo+ICsKPiArCXJldHVybiBQVFJfRVJSX09SX1pFUk8oaHdtb25fZGV2KTsKPiArfQo+ICsK PiArc3RhdGljIHN0cnVjdCBwbGF0Zm9ybV9kcml2ZXIgaWJtcG93ZXJudl9kcml2ZXIgPSB7Cj4g KwkuZHJpdmVyID0gewo+ICsJCS5vd25lciA9IFRISVNfTU9EVUxFLAo+ICsJCS5uYW1lID0gRFJW TkFNRSwKPiArCX0sCj4gK307Cj4gKwo+ICtzdGF0aWMgaW50IF9faW5pdCBpYm1wb3dlcm52X2lu aXQodm9pZCkKPiArewo+ICsJaW50IGVycjsKPiArCj4gKwlwZGV2aWNlID0gcGxhdGZvcm1fZGV2 aWNlX2FsbG9jKERSVk5BTUUsIDApOwo+ICsJaWYgKCFwZGV2aWNlKSB7Cj4gKwkJcHJfZXJyKCIl czogRGV2aWNlIGFsbG9jYXRpb24gZmFpbGVkXG4iLCBfX2Z1bmNfXyk7Cj4gKwkJZXJyID0gLUVO T01FTTsKPiArCQlnb3RvIGV4aXQ7Cj4gKwl9Cj4gKwo+ICsJZXJyID0gcGxhdGZvcm1fZGV2aWNl X2FkZChwZGV2aWNlKTsKPiArCWlmIChlcnIpIHsKPiArCQlwcl9lcnIoIiVzOiBEZXZpY2UgYWRk aXRpb24gZmFpbGVkICglZClcbiIsIF9fZnVuY19fLCBlcnIpOwo+ICsJCWdvdG8gZXhpdF9kZXZp Y2VfcHV0Owo+ICsJfQo+ICsKPiArCWVyciA9IHBsYXRmb3JtX2RyaXZlcl9wcm9iZSgmaWJtcG93 ZXJudl9kcml2ZXIsIGlibXBvd2VybnZfcHJvYmUpOwo+ICsJaWYgKGVycikgewo+ICsJCXByX2Vy cigiJXM6IFBsYXRmcm9tIGRyaXZlciBwcm9iZSBmYWlsZWRcbiIsIF9fZnVuY19fKTsKPiArCQln b3RvIGV4aXRfZGV2aWNlX2RlbDsKPiArCX0KPiArCj4gKwlyZXR1cm4gMDsKPiArCj4gK2V4aXRf ZGV2aWNlX2RlbDoKPiArCXBsYXRmb3JtX2RldmljZV9kZWwocGRldmljZSk7Cj4gK2V4aXRfZGV2 aWNlX3B1dDoKPiArCXBsYXRmb3JtX2RldmljZV9wdXQocGRldmljZSk7Cj4gK2V4aXQ6Cj4gKwly ZXR1cm4gZXJyOwo+ICt9Cj4gKwo+ICtzdGF0aWMgdm9pZCBfX2V4aXQgaWJtcG93ZXJudl9leGl0 KHZvaWQpCj4gK3sKPiArCXBsYXRmb3JtX2RyaXZlcl91bnJlZ2lzdGVyKCZpYm1wb3dlcm52X2Ry aXZlcik7Cj4gKwlwbGF0Zm9ybV9kZXZpY2VfdW5yZWdpc3RlcihwZGV2aWNlKTsKPiArfQo+ICsK PiArTU9EVUxFX0FVVEhPUigiTmVlbGVzaCBHdXB0YSA8bmVlbGVndXBAbGludXgudm5ldC5pYm0u Y29tPiIpOwo+ICtNT0RVTEVfREVTQ1JJUFRJT04oIklCTSBQT1dFUk5WIHBsYXRmb3JtIHNlbnNv cnMiKTsKPiArTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOwo+ICsKPiArbW9kdWxlX2luaXQoaWJtcG93 ZXJudl9pbml0KTsKPiArbW9kdWxlX2V4aXQoaWJtcG93ZXJudl9leGl0KTsKPgo+IF9fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fCj4gTGludXhwcGMtZGV2IG1h aWxpbmcgbGlzdAo+IExpbnV4cHBjLWRldkBsaXN0cy5vemxhYnMub3JnCj4gaHR0cHM6Ly9saXN0 cy5vemxhYnMub3JnL2xpc3RpbmZvL2xpbnV4cHBjLWRldgoKX19fX19fX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX18KbG0tc2Vuc29ycyBtYWlsaW5nIGxpc3QKbG0tc2Vu c29yc0BsbS1zZW5zb3JzLm9yZwpodHRwOi8vbGlzdHMubG0tc2Vuc29ycy5vcmcvbWFpbG1hbi9s aXN0aW5mby9sbS1zZW5zb3Jz ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-26 6:34 ` [lm-sensors] " Neelesh Gupta @ 2014-05-26 14:12 ` Guenter Roeck -1 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-05-26 14:12 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 05/25/2014 11:22 PM, Neelesh Gupta wrote: > Any updates on the patch. > Not yet, I have been too busy with other stuff. That happens, unfortunately. Guenter _______________________________________________ lm-sensors mailing list lm-sensors@lm-sensors.org http://lists.lm-sensors.org/mailman/listinfo/lm-sensors ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-26 14:12 ` Guenter Roeck 0 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-05-26 14:12 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 05/25/2014 11:22 PM, Neelesh Gupta wrote: > Any updates on the patch. > Not yet, I have been too busy with other stuff. That happens, unfortunately. Guenter ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-19 14:38 ` [lm-sensors] " Neelesh Gupta @ 2014-05-28 7:23 ` Guenter Roeck -1 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-05-28 7:23 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat T24gMDUvMTkvMjAxNCAwNzoyNiBBTSwgTmVlbGVzaCBHdXB0YSB3cm90ZToKPiBUaGlzIHBhdGNo IGFkZHMgYmFzaWMga2VybmVsIGVuYWJsZW1lbnQgZm9yIHJlYWRpbmcgcG93ZXIgdmFsdWVzLCBm YW4KPiBzcGVlZCBycG0gYW5kIHRlbXBlcmF0dXJlIHZhbHVlcyBvbiBwb3dlcm52IHBsYXRmb3Jt cyB3aGljaCB3aWxsCj4gYmUgZXhwb3J0ZWQgdG8gdXNlciBzcGFjZSB0aHJvdWdoIHN5c2ZzIGlu dGVyZmFjZS4KPgo+IFRlc3QgcmVzdWx0czoKPiAtLS0tLS0tLS0tLS0tCj4gW3Jvb3RAdHVsMTYz cDEgfl0jIHNlbnNvcnMKPiBpYm1wb3dlcm52LWlzYS0wMDAwCj4gQWRhcHRlcjogSVNBIGFkYXB0 ZXIKPiBmYW4xOiAgICAgICAgNTQ4NyBSUE0gIChtaW4gPSAgICAwIFJQTSkKPiBmYW4yOiAgICAg ICAgNTE1MiBSUE0gIChtaW4gPSAgICAwIFJQTSkKPiBmYW4zOiAgICAgICAgNTU5MCBSUE0gICht aW4gPSAgICAwIFJQTSkKPiBmYW40OiAgICAgICAgNDk2MyBSUE0gIChtaW4gPSAgICAwIFJQTSkK PiBmYW41OiAgICAgICAgICAgMCBSUE0gIChtaW4gPSAgICAwIFJQTSkKPiBmYW42OiAgICAgICAg ICAgMCBSUE0gIChtaW4gPSAgICAwIFJQTSkKPiBmYW43OiAgICAgICAgNzQ4OCBSUE0gIChtaW4g PSAgICAwIFJQTSkKPiBmYW44OiAgICAgICAgNzk0NCBSUE0gIChtaW4gPSAgICAwIFJQTSkKPiB0 ZW1wMTogICAgICAgICszOS4wwrBDICAoaGlnaCA9ICArMC4wwrBDKQo+IHBvd2VyMTogICAgICAx OTIuMDAgVwo+Cj4gW3Jvb3RAdHVsMTYzcDEgfl0jIGxzIC9zeXMvZGV2aWNlcy9wbGF0Zm9ybS8K PiBhbGFybXRpbWVyICBpYm1wb3dlcm52LjAgIHJ0Yy1nZW5lcmljICBzZXJpYWw4MjUwICB1ZXZl bnQKPiBbcm9vdEB0dWwxNjNwMSB+XSMgbHMgL3N5cy9kZXZpY2VzL3BsYXRmb3JtL2libXBvd2Vy bnYuMC8KPiBkcml2ZXIvICAgIGh3bW9uLyAgICAgbW9kYWxpYXMgICBzdWJzeXN0ZW0vIHVldmVu dAo+IFtyb290QHR1bDE2M3AxIH5dIyBscyAvc3lzL2RldmljZXMvcGxhdGZvcm0vaWJtcG93ZXJu di4wL2h3bW9uL2h3bW9uMC8KPiBkZXZpY2UJICAgIGZhbjJfbWluCWZhbjRfbWluICAgIGZhbjZf bWluCWZhbjhfbWluICAgcG93ZXIxX2lucHV0Cj4gZmFuMV9mYXVsdCAgZmFuM19mYXVsdAlmYW41 X2ZhdWx0ICBmYW43X2ZhdWx0CWluMV9mYXVsdCAgc3Vic3lzdGVtCj4gZmFuMV9pbnB1dCAgZmFu M19pbnB1dAlmYW41X2lucHV0ICBmYW43X2lucHV0CWluMl9mYXVsdCAgdGVtcDFfaW5wdXQKPiBm YW4xX21pbiAgICBmYW4zX21pbglmYW41X21pbiAgICBmYW43X21pbglpbjNfZmF1bHQgIHRlbXAx X21heAo+IGZhbjJfZmF1bHQgIGZhbjRfZmF1bHQJZmFuNl9mYXVsdCAgZmFuOF9mYXVsdAlpbjRf ZmF1bHQgIHVldmVudAo+IGZhbjJfaW5wdXQgIGZhbjRfaW5wdXQJZmFuNl9pbnB1dCAgZmFuOF9p bnB1dAluYW1lCj4gW3Jvb3RAdHVsMTYzcDEgfl0jCj4gW3Jvb3RAdHVsMTYzcDEgfl0jIGxzIC9z eXMvY2xhc3MvaHdtb24vaHdtb24wLwo+IGRldmljZQkgICAgZmFuMl9taW4JZmFuNF9taW4gICAg ZmFuNl9taW4JZmFuOF9taW4gICBwb3dlcjFfaW5wdXQKPiBmYW4xX2ZhdWx0ICBmYW4zX2ZhdWx0 CWZhbjVfZmF1bHQgIGZhbjdfZmF1bHQJaW4xX2ZhdWx0ICBzdWJzeXN0ZW0KPiBmYW4xX2lucHV0 ICBmYW4zX2lucHV0CWZhbjVfaW5wdXQgIGZhbjdfaW5wdXQJaW4yX2ZhdWx0ICB0ZW1wMV9pbnB1 dAo+IGZhbjFfbWluICAgIGZhbjNfbWluCWZhbjVfbWluICAgIGZhbjdfbWluCWluM19mYXVsdCAg dGVtcDFfbWF4Cj4gZmFuMl9mYXVsdCAgZmFuNF9mYXVsdAlmYW42X2ZhdWx0ICBmYW44X2ZhdWx0 CWluNF9mYXVsdCAgdWV2ZW50Cj4gZmFuMl9pbnB1dCAgZmFuNF9pbnB1dAlmYW42X2lucHV0ICBm YW44X2lucHV0CW5hbWUKPiBbcm9vdEB0dWwxNjNwMSB+XSMKPgoKClRoZSBpblhfZmF1bHQgYXR0 cmlidXRlcyBkb24ndCByZWFsbHkgbWFrZSBtdWNoIHNlbnNlLiBfZmF1bHQgYXR0cmlidXRlcyB3 aXRob3V0Cl9pbnB1dCBhdHRyaWJ1dGVzIGRvbid0IGhhdmUgYW55IHZhbHVlIGFuZCBhcmUsIGFz IHlvdSBub3RpY2VkLCBub3QgZGlzcGxheWVkCndpdGggdGhlIHNlbnNvcnMgY29tbWFuZC4gSXMg dGhpcyBhIHByb2JsZW0gaW4gdGVoIGRldmljZXRyZWUgZGF0YSBvciBkbyB5b3UKcmVhbGx5IGhh dmUgdm9sdGFnZSBmYXVsdHMgd2l0aG91dCB2b2x0YWdlcyA/Cgo+IFNpZ25lZC1vZmYtYnk6IE5l ZWxlc2ggR3VwdGEgPG5lZWxlZ3VwQGxpbnV4LnZuZXQuaWJtLmNvbT4KPiAtLS0KPgpDaGVja3Bh dGNoIHNheXM6Cgp0b3RhbDogOCBlcnJvcnMsIDExIHdhcm5pbmdzLCAzODkgbGluZXMgY2hlY2tl ZAoKTk9URTogd2hpdGVzcGFjZSBlcnJvcnMgZGV0ZWN0ZWQsIHlvdSBtYXkgd2lzaCB0byB1c2Ug c2NyaXB0cy9jbGVhbnBhdGNoIG9yCiAgICAgICBzY3JpcHRzL2NsZWFuZmlsZQoKd2hpY2ggc2hv dWxkIHJlYWxseSBub3QgaGFwcGVuIGF0IHRoaXMgcG9pbnQuCgpQbGVhc2UgbWFrZSBzdXJlIHlv dSBmb2xsb3cgQ29kaW5nU3R5bGUuIGNoZWNrcGF0Y2ggLS1zdHJpY3QgcG9pbnRzIHRvIGEgbnVt YmVyCm9mIGFkZGl0aW9uYWwgdmlvbGF0aW9ucy4KCk1vcmUgY29tbWVudHMgaW5saW5lLgoKPiBD aGFuZ2VzIGluIHYyCj4gPT09PT09PT09PT09PQo+IC0gR2VuZXJpYyB1c2Ugb2YgZGV2bV8qIGZ1 bmN0aW9ucyBpbiBod21vbiBsaWtlIHVzaW5nIGRldm1fa3phbGxvYygpIGZvciBkeW5hbWljCj4g ICAgbWVtb3J5IHJlcXVlc3QsIGF2b2lkaW5nIHRoZSBuZWVkIHRvIGV4cGxpY2l0IGZyZWUgb2Yg bWVtb3J5Lgo+ICAgIEFkZGluZyAnc3RydWN0IGF0dHJpYnV0ZV9ncm91cCcgYXMgbWVtYmVyIG9m IHBsYXRmb3JtIGRhdGEgc3RydWN0dXJlIHRvIGJlCj4gICAgcG9wdWxhdGVkIGFuZCB0aGVuIHBh c3NlZCB0byBkZXZtX2h3bW9uX2RldmljZV9yZWdpc3Rlcl93aXRoX2dyb3VwcygpLgo+Cj4gICAg Tm90ZTogSGF2aW5nIGFuIGFycmF5IG9mIHBvaW50ZXJzIG9mICdhdHRyaWJ1dGVfZ3JvdXAnIGFu ZCBlYWNoIGdyb3VwCj4gICAgY29ycmVzcG9uZHMgdG8gJ2VudW0gc2Vuc29ycycgdHlwZS4gTm90 IGNvbXBsZXRlbHkgc3VyZSwgaWYgaXQncyBpZGVhbCBvcgo+ICAgIGNvdWxkIGhhdmUganVzdCBv bmUgZ3JvdXAgcG9wdWxhdGVkIHdpdGggYXR0cmlidXRlcyBvZiBzZW5zb3IgdHlwZXM/Cj4KWW91 ciBjYWxsLCByZWFsbHk7IHdoYXRldmVyIGlzIGVhc2llciBmb3IgeW91LiBJIHdvbid0IGRpY3Rh dGUgb25lIG9yIHRoZSBvdGhlci4KClF1ZXN0aW9uIHRob3VnaCBpcyB3aGF0IGhhcHBlbnMgaWYg b25lIGdyb3VwIGlzIG5vdCBwb3B1bGF0ZWQuIElmIEkgdW5kZXJzdGFuZAp0aGUgY29kZSBjb3Jy ZWN0bHkgdGhpcyB3aWxsIHJlc3VsdCBpbiB0aGUgcmVtYWluaW5nIGdyb3VwcyB0byBiZSAnZHJv cHBlZCcsCmllIG5vdCBkaXNwbGF5ZWQgYXQgYWxsLgoKPiAtICdpYm1wb3dlcm52JyBpcyBub3Qg aG90LXBsdWdnYWJsZSBkZXZpY2Ugc28gbW92aW5nICdwbGF0Zm9ybV9kcml2ZXInIGNhbGxiYWNr Cj4gICAgZnVuY3Rpb24gKHByb2JlKSBhcyBwYXJ0IG9mIF9faW5pdCBjb2RlLgo+IC0gRml4ZWQg aXNzdWVzIHJlbGF0ZWQgdG8gY29kaW5nIHN0eWxlLgo+IC0gT3RoZXIgZ2VuZXJhbCBjb21tZW50 cyBpbiB2MS4KPgo+ICAgZHJpdmVycy9od21vbi9LY29uZmlnICAgICAgfCAgICA4ICsKPiAgIGRy aXZlcnMvaHdtb24vTWFrZWZpbGUgICAgIHwgICAgMQo+ICAgZHJpdmVycy9od21vbi9pYm1wb3dl cm52LmMgfCAgMzY4ICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysr CgpZb3UnbGwgYWxzbyBuZWVkIERvY3VtZW50YXRpb24vaHdtb24vaWJtcG93ZXJudiBhbmQKRG9j dW1lbnRhdGlvbi9kZXZpY2V0cmVlL2JpbmRpbmdzL2h3bW9uL2libXBvd2VybnYuCgpUaGUgbGF0 dGVyIHdpbGwgbmVlZCB0byBnZXQgYW4gQWNrIGZyb20gdGhlIGRldmljZXRyZWUgbWFpbnRhaW5l cnMuCgo+ICAgMyBmaWxlcyBjaGFuZ2VkLCAzNzcgaW5zZXJ0aW9ucygrKQo+ICAgY3JlYXRlIG1v ZGUgMTAwNjQ0IGRyaXZlcnMvaHdtb24vaWJtcG93ZXJudi5jCj4KPiBkaWZmIC0tZ2l0IGEvZHJp dmVycy9od21vbi9LY29uZmlnIGIvZHJpdmVycy9od21vbi9LY29uZmlnCj4gaW5kZXggYmMxOTZm NC4uM2UzMDhmYSAxMDA2NDQKPiAtLS0gYS9kcml2ZXJzL2h3bW9uL0tjb25maWcKPiArKysgYi9k cml2ZXJzL2h3bW9uL0tjb25maWcKPiBAQCAtNTU0LDYgKzU1NCwxNCBAQCBjb25maWcgU0VOU09S U19JQk1QRVgKPiAgIAkgIFRoaXMgZHJpdmVyIGNhbiBhbHNvIGJlIGJ1aWx0IGFzIGEgbW9kdWxl LiAgSWYgc28sIHRoZSBtb2R1bGUKPiAgIAkgIHdpbGwgYmUgY2FsbGVkIGlibXBleC4KPgo+ICtj b25maWcgU0VOU09SU19JQk1QT1dFUk5WCj4gKwl0cmlzdGF0ZSAiSUJNIFBPV0VSTlYgcGxhdGZv cm0gc2Vuc29ycyIKPiArCWRlcGVuZHMgb24gUFBDX1BPV0VSTlYKPiArCWRlZmF1bHQgeQo+ICsJ aGVscAo+ICsJICBJZiB5b3Ugc2F5IHllcyBoZXJlIHlvdSBnZXQgc3VwcG9ydCBmb3IgdGhlIHRl bXBlcmF0dXJlL2Zhbi9wb3dlcgo+ICsJICBzZW5zb3JzIG9uIHlvdXIgcGxhdGZvcm0uCj4gKwo+ ICAgY29uZmlnIFNFTlNPUlNfSUlPX0hXTU9OCj4gICAJdHJpc3RhdGUgIkh3bW9uIGRyaXZlciB0 aGF0IHVzZXMgY2hhbm5lbHMgc3BlY2lmaWVkIHZpYSBpaW8gbWFwcyIKPiAgIAlkZXBlbmRzIG9u IElJTwo+IGRpZmYgLS1naXQgYS9kcml2ZXJzL2h3bW9uL01ha2VmaWxlIGIvZHJpdmVycy9od21v bi9NYWtlZmlsZQo+IGluZGV4IGM0OGY5ODcuLjE5OWM0MDEgMTAwNjQ0Cj4gLS0tIGEvZHJpdmVy cy9od21vbi9NYWtlZmlsZQo+ICsrKyBiL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUKPiBAQCAtNzEs NiArNzEsNyBAQCBvYmotJChDT05GSUdfU0VOU09SU19VTFRSQTQ1KQkrPSB1bHRyYTQ1X2Vudi5v Cj4gICBvYmotJChDT05GSUdfU0VOU09SU19JNUtfQU1CKQkrPSBpNWtfYW1iLm8KPiAgIG9iai0k KENPTkZJR19TRU5TT1JTX0lCTUFFTSkJKz0gaWJtYWVtLm8KPiAgIG9iai0kKENPTkZJR19TRU5T T1JTX0lCTVBFWCkJKz0gaWJtcGV4Lm8KPiArb2JqLSQoQ09ORklHX1NFTlNPUlNfSUJNUE9XRVJO VikrPSBpYm1wb3dlcm52Lm8KPiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0lJT19IV01PTikgKz0g aWlvX2h3bW9uLm8KPiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0lOQTIwOSkJKz0gaW5hMjA5Lm8K PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0lOQTJYWCkJKz0gaW5hMnh4Lm8KPiBkaWZmIC0tZ2l0 IGEvZHJpdmVycy9od21vbi9pYm1wb3dlcm52LmMgYi9kcml2ZXJzL2h3bW9uL2libXBvd2VybnYu Ywo+IG5ldyBmaWxlIG1vZGUgMTAwNjQ0Cj4gaW5kZXggMDAwMDAwMC4uYWZjZTYyMAo+IC0tLSAv ZGV2L251bGwKPiArKysgYi9kcml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwo+IEBAIC0wLDAgKzEs MzY4IEBACj4gKy8qCj4gKyAqIElCTSBQb3dlck5WIHBsYXRmb3JtIHNlbnNvcnMgZm9yIHRlbXBl cmF0dXJlL2Zhbi9wb3dlcgo+ICsgKiBDb3B5cmlnaHQgKEMpIDIwMTQgSUJNCj4gKyAqCj4gKyAq IFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBh bmQvb3IgbW9kaWZ5Cj4gKyAqIGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwg UHVibGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5Cj4gKyAqIHRoZSBGcmVlIFNvZnR3YXJlIEZv dW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCj4gKyAqIChhdCB5 b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCj4gKyAqCj4gKyAqIFRoaXMgcHJvZ3JhbSBp cyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAo+ICsgKiBi dXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50 eSBvZgo+ICsgKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBV UlBPU0UuICBTZWUgdGhlCj4gKyAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3Jl IGRldGFpbHMuCj4gKyAqCj4gKyAqIFlvdSBzaG91bGQgaGF2ZSByZWNlaXZlZCBhIGNvcHkgb2Yg dGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlCj4gKyAqIGFsb25nIHdpdGggdGhpcyBwcm9n cmFtLgo+ICsgKi8KPiArCj4gKyNpbmNsdWRlIDxsaW51eC9pbml0Lmg+Cj4gKyNpbmNsdWRlIDxs aW51eC9tb2R1bGUuaD4KPiArI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgo+ICsjaW5jbHVkZSA8 bGludXgvaHdtb24uaD4KPiArI2luY2x1ZGUgPGxpbnV4L2h3bW9uLXN5c2ZzLmg+Cj4gKyNpbmNs dWRlIDxsaW51eC9vZi5oPgo+ICsjaW5jbHVkZSA8bGludXgvc2xhYi5oPgo+ICsKPiArI2luY2x1 ZGUgPGxpbnV4L3BsYXRmb3JtX2RldmljZS5oPgo+ICsjaW5jbHVkZSA8YXNtL29wYWwuaD4KPiAr I2luY2x1ZGUgPGxpbnV4L2Vyci5oPgo+ICsKPiArI2RlZmluZSBEUlZOQU1FCQkiaWJtcG93ZXJu diIKPiArI2RlZmluZSBNQVhfQVRUUl9MRU4JMzIKPiArCj4gKy8qIFNlbnNvciBzdWZmaXggbmFt ZSBmcm9tIERUICovCj4gKyNkZWZpbmUgRFRfRkFVTFRfQVRUUl9TVUZGSVgJCSJmYXVsdGVkIgo+ ICsjZGVmaW5lIERUX0RBVEFfQVRUUl9TVUZGSVgJCSJkYXRhIgo+ICsjZGVmaW5lIERUX1RIUkVT SE9MRF9BVFRSX1NVRkZJWAkidGhycyIKPiArCj4gKy8qCj4gKyAqIEVudW1lcmF0ZXMgYWxsIHRo ZSB0eXBlcyBvZiBzZW5zb3JzIGluIHRoZSBQT1dFUk5WIHBsYXRmb3JtIGFuZCBkb2VzIGluZGV4 Cj4gKyAqIGludG8gJ3N0cnVjdCBzZW5zb3JfZ3JvdXAnCj4gKyAqLwo+ICtlbnVtIHNlbnNvcnMg ewo+ICsJRkFOLAo+ICsJQU1CSUVOVF9URU1QLAo+ICsJUE9XRVJfU1VQUExZLAo+ICsJUE9XRVJf SU5QVVQsCj4gKwlNQVhfU0VOU09SX1RZUEUsCj4gK307Cj4gKwo+ICtzdGF0aWMgc3RydWN0IHNl bnNvcl9ncm91cCB7Cj4gKwljb25zdCBjaGFyICpuYW1lOwo+ICsJY29uc3QgY2hhciAqY29tcGF0 aWJsZTsKPiArCXN0cnVjdCBhdHRyaWJ1dGVfZ3JvdXAgZ3JvdXA7Cj4gKwl1MzIgYXR0cl9jb3Vu dDsKPiArfSBzZW5zb3JfZ3JvdXBzW10gPSB7Cj4gKwl7ImZhbiIsICJpYm0sb3BhbC1zZW5zb3It Y29vbGluZy1mYW4iLCB7MH0sIDB9LAo+ICsJeyJ0ZW1wIiwgImlibSxvcGFsLXNlbnNvci1hbWIt dGVtcCIsIHswfSwgMH0sCj4gKwl7ImluIiwgImlibSxvcGFsLXNlbnNvci1wb3dlci1zdXBwbHki LCB7MH0sIDB9LAo+ICsJeyJwb3dlciIsICJpYm0sb3BhbC1zZW5zb3ItcG93ZXIiLCB7MH0sIDB9 Cj4gK307Cj4gKwpUaGUgJzAnIGluaXRpYWxpemF0aW9ucyBzaG91bGQgbm90IGJlIG5lY2Vzc2Fy eS4KCgo+ICtzdHJ1Y3Qgc2Vuc29yX2RhdGEgewo+ICsJdTMyIGlkOyAvKiBBbiBvcGFxdWUgaWQg b2YgdGhlIGZpcm13YXJlIGZvciBlYWNoIHNlbnNvciAqLwo+ICsJZW51bSBzZW5zb3JzIHR5cGU7 Cj4gKwljaGFyIG5hbWVbTUFYX0FUVFJfTEVOXTsKPiArCXN0cnVjdCBkZXZpY2VfYXR0cmlidXRl IGRldl9hdHRyOwo+ICt9Owo+ICsKPiArc3RydWN0IHBsYXRmb3JtX2RhdGEgewo+ICsJY29uc3Qg c3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqYXR0cl9ncm91cHNbTUFYX1NFTlNPUl9UWVBFICsgMV07 Cj4gKwl1MzIgc2Vuc29yc19jb3VudDsgLyogVG90YWwgY291bnQgb2Ygc2Vuc29ycyBmcm9tIGVh Y2ggZ3JvdXAgKi8KPiArfTsKPiArCj4gKy8qIFBsYXRmb3JtIGRldmljZSByZXByZXNlbnRpbmcg YWxsIHRoZSBpYm1wb3dlcm52IHNlbnNvcnMgKi8KPiArc3RhdGljIHN0cnVjdCBwbGF0Zm9ybV9k ZXZpY2UgKnBkZXZpY2U7Cj4gKwo+ICtzdGF0aWMgc3NpemVfdCBzaG93X3NlbnNvcihzdHJ1Y3Qg ZGV2aWNlICpkZXYsIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICpkZXZhdHRyLAo+ICsJCQkgICBj aGFyICpidWYpCj4gK3sKPiArCXN0cnVjdCBzZW5zb3JfZGF0YSAqc2RhdGEgPSBjb250YWluZXJf b2YoZGV2YXR0ciwgc3RydWN0IHNlbnNvcl9kYXRhLAo+ICsJCQkJCQkgZGV2X2F0dHIpOwo+ICsJ c3NpemVfdCByZXQ7Cj4gKwl1MzIgeDsKPiArCj4gKwlyZXQgPSBvcGFsX2dldF9zZW5zb3JfZGF0 YShzZGF0YS0+aWQsICZ4KTsKPiArCWlmIChyZXQpIHsKPiArCQlwcl9lcnIoIiVzOiBGYWlsZWQg dG8gZ2V0IG9wYWwgc2Vuc29yIGRhdGFcbiIsIF9fZnVuY19fKTsKPiArCQlyZXR1cm4gcmV0Owo+ ICsJfQo+ICsKPiArCS8qIENvbnZlcnQgdGVtcGVyYXR1cmUgdG8gbWlsbGktZGVncmVlcyAqLwo+ ICsJaWYgKHNkYXRhLT50eXBlID09IEFNQklFTlRfVEVNUCkKPiArCQl4ICo9IDEwMDA7Cj4gKwkv KiBDb252ZXJ0IHBvd2VyIHRvIG1pY3JvLXdhdHRzICovCj4gKwllbHNlIGlmIChzZGF0YS0+dHlw ZSA9PSBQT1dFUl9JTlBVVCkKPiArCQl4ICo9IDEwMDAwMDA7Cj4gKwo+ICsJcmV0dXJuIHNwcmlu dGYoYnVmLCAiJWRcbiIsIHgpOwoKeCBpcyB1bnNpZ25lZCwgc28gJXUuCgo+ICt9Cj4gKwo+ICtz dGF0aWMgdm9pZCBfX2luaXQgZ2V0X3NlbnNvcl9pbmRleF9hdHRyKGNvbnN0IGNoYXIgKm5hbWUs IHUzMiAqaW5kZXgsIGNoYXIgKmF0dHIpCj4gK3sKPiArCWNoYXIgKmhhc2hfcG9zID0gc3RyY2hy KG5hbWUsICcjJyk7Cj4gKwljaGFyICpkYXNoX3BvczsKPiArCXUzMiBjb3B5X2xlbjsKPiArCWNo YXIgYnVmWzhdOwo+ICsKPiArCW1lbXNldChidWYsIDAsIHNpemVvZihidWYpKTsKPiArCSppbmRl eCA9IDA7Cj4gKwkqYXR0ciA9ICdcMCc7Cj4gKwo+ICsJaWYgKGhhc2hfcG9zKSB7Cj4gKwkJZGFz aF9wb3MgPSBzdHJjaHIoaGFzaF9wb3MsICctJyk7Cj4gKwkJaWYgKGRhc2hfcG9zKSB7Cj4gKwkJ CWNvcHlfbGVuID0gZGFzaF9wb3MgLSBoYXNoX3BvcyAtIDE7Cj4gKwkJCWlmIChjb3B5X2xlbiA8 IHNpemVvZihidWYpKSB7Cj4gKwkJCQlzdHJuY3B5KGJ1ZiwgaGFzaF9wb3MgKyAxLCBjb3B5X2xl bik7Cj4gKwkJCQlzc2NhbmYoYnVmLCAiJWQiLCBpbmRleCk7CgpXaGF0IGlmIHNzY2FuZiBmYWls cyA/IE1pZ2h0IGJlIGFuIGludGVyZXN0aW5nIGV4ZXJjaXNlIHRvIHRyeSBhbmQgY3JlYXRlCm11 bHRpcGxlIHNlbnNvcnMgd2l0aCBpbmRleCAwIChvciwgZm9yIHRoYXQgbWF0dGVyLCB3aXRoIHRo ZSBzYW1lIGluZGV4IHZhbHVlKS4KRG8geW91IGhhdmUgYW55IHByb3RlY3Rpb24gYWdhaW5zdCBi YWQgaW5wdXQgZGF0YSA/IEd1ZXNzIG5vdDsgZGlkIHlvdSB0ZXN0CndoYXQgaGFwcGVucyBpZiB5 b3UgcGFzcyBiYWQgZGF0YSB0byB0aGUgZHJpdmVyIChzdWNoIGFzIGR1cGxpY2F0ZSBzZW5zb3IK ZW50cmllcykgPwoKPiArCQkJfQo+ICsKPiArCQkJc3RybmNweShhdHRyLCBkYXNoX3BvcyArIDEs IE1BWF9BVFRSX0xFTik7Cj4gKwkJfQo+ICsJfQo+ICt9Cj4gKwo+ICsvKgo+ICsgKiBUaGlzIGZ1 bmN0aW9uIHRyYW5zbGF0ZXMgdGhlIERUIG5vZGUgbmFtZSBpbnRvIHRoZSAnaHdtb24nIGF0dHJp YnV0ZSBuYW1lLgo+ICsgKiBJQk1QT1dFUk5WIGRldmljZSBub2RlIGFwcGVhciBsaWtlIGNvb2xp bmctZmFuIzItZGF0YSwgYW1iLXRlbXAjMS10aHJzIGV0Yy4KPiArICogd2hpY2ggbmVlZCB0byBi ZSBtYXBwZWQgYXMgZmFuMl9pbnB1dCwgdGVtcDFfbWF4IHJlc3BlY3RpdmVseSBiZWZvcmUKPiAr ICogcG9wdWxhdGluZyB0aGVtIGluc2lkZSBod21vbiBkZXZpY2UgY2xhc3MuLgo+ICsgKi8KPiAr c3RhdGljIGludCBfX2luaXQgY3JlYXRlX2h3bW9uX2F0dHJfbmFtZShlbnVtIHNlbnNvcnMgdHlw ZSwgY29uc3QgY2hhciAqbm9kZV9uYW1lLAo+ICsJCQkJICBjaGFyICpod21vbl9hdHRyX25hbWUp Cj4gK3sKPiArCWNoYXIgYXR0cl9zdWZmaXhbTUFYX0FUVFJfTEVOXTsKPiArCWNoYXIgKmF0dHJf bmFtZTsKPiArCXUzMiBpbmRleDsKPiArCj4gKwlnZXRfc2Vuc29yX2luZGV4X2F0dHIobm9kZV9u YW1lLCAmaW5kZXgsIGF0dHJfc3VmZml4KTsKPiArCWlmICghaW5kZXggfHwgIXN0cmxlbihhdHRy X3N1ZmZpeCkpIHsKPiArCQlwcl9pbmZvKCIlczogU2Vuc29yIGRldmljZSBub2RlIG5hbWUgaXMg aW52YWxpZCwgbmFtZTogJXNcbiIsCj4gKwkJCQlfX2Z1bmNfXywgbm9kZV9uYW1lKTsKPiArCQly ZXR1cm4gLUVJTlZBTDsKPiArCX0KPiArCj4gKwlpZiAoIXN0cmNtcChhdHRyX3N1ZmZpeCwgRFRf RkFVTFRfQVRUUl9TVUZGSVgpKQo+ICsJCWF0dHJfbmFtZSA9ICJmYXVsdCI7Cj4gKwllbHNlIGlm KCFzdHJjbXAoYXR0cl9zdWZmaXgsIERUX0RBVEFfQVRUUl9TVUZGSVgpKQo+ICsJCWF0dHJfbmFt ZSA9ICJpbnB1dCI7Cj4gKwllbHNlIGlmICghc3RyY21wKGF0dHJfc3VmZml4LCBEVF9USFJFU0hP TERfQVRUUl9TVUZGSVgpKSB7Cj4gKwkJaWYgKHR5cGUgPT0gQU1CSUVOVF9URU1QKQo+ICsJCQlh dHRyX25hbWUgPSAibWF4IjsKPiArCQllbHNlIGlmICh0eXBlID09IEZBTikKPiArCQkJYXR0cl9u YW1lID0gIm1pbiI7Cj4gKwkJZWxzZQo+ICsJCQlyZXR1cm4gLUVOT0VOVDsKPiArCX0gZWxzZQo+ ICsJCXJldHVybiAtRU5PRU5UOwo+ICsKPiArCXNucHJpbnRmKGh3bW9uX2F0dHJfbmFtZSwgTUFY X0FUVFJfTEVOLCAiJXMlZF8lcyIsCj4gKwkJCXNlbnNvcl9ncm91cHNbdHlwZV0ubmFtZSwgaW5k ZXgsIGF0dHJfbmFtZSk7Cj4gKwlyZXR1cm4gMDsKPiArfQo+ICsKPiArc3RhdGljIGludCBfX2lu aXQgcG9wdWxhdGVfYXR0cl9ncm91cHMoc3RydWN0IHBsYXRmb3JtX2RldmljZSAqcGRldikKPiAr ewo+ICsJc3RydWN0IHBsYXRmb3JtX2RhdGEgKnBkYXRhID0gcGxhdGZvcm1fZ2V0X2RydmRhdGEo cGRldik7Cj4gKwljb25zdCBzdHJ1Y3QgYXR0cmlidXRlX2dyb3VwICoqcGdyb3VwcyA9IHBkYXRh LT5hdHRyX2dyb3VwczsKPiArCXN0cnVjdCBkZXZpY2Vfbm9kZSAqb3BhbCwgKm5wOwo+ICsJZW51 bSBzZW5zb3JzIHR5cGU7Cj4gKwlpbnQgZXJyID0gMDsKPiArCj4gKwlvcGFsID0gb2ZfZmluZF9u b2RlX2J5X3BhdGgoIi9pYm0sb3BhbC9zZW5zb3JzIik7Cj4gKyAgICAgICAgaWYgKCFvcGFsKSB7 CgpBbiBvYnZpb3VzIHdoaXRlc3BhY2UgZXJyb3IgaGVyZS4KCj4gKwkJcHJfZXJyKCIlczogT3Bh bCAnc2Vuc29ycycgbm9kZSBub3QgZm91bmRcbiIsIF9fZnVuY19fKTsKPiArCQlyZXR1cm4gLUVO T0RFVjsKPiArICAgICAgICB9Cj4gKwo+ICsJZm9yX2VhY2hfY2hpbGRfb2Zfbm9kZShvcGFsLCBu cCkgewo+ICsJCWlmIChucC0+bmFtZSA9PSBOVUxMKQo+ICsJCQljb250aW51ZTsKPiArCj4gKwkJ Zm9yICh0eXBlID0gMDsgdHlwZSA8IE1BWF9TRU5TT1JfVFlQRTsgdHlwZSsrKQo+ICsJCQlpZiAo b2ZfZGV2aWNlX2lzX2NvbXBhdGlibGUobnAsCj4gKwkJCQlzZW5zb3JfZ3JvdXBzW3R5cGVdLmNv bXBhdGlibGUpKSB7Cj4gKwkJCQlzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQrKzsKPiAr CQkJCWJyZWFrOwo+ICsJCQl9Cj4gKwl9CgpZb3Ugc2hvdWxkIGJlIGFibGUgdG8gZG8KCW9mX25v ZGVfcHV0KG9wYWwpOwoKaGVyZS4gVGhlbiB5b3UgY2FuIHJldHVybiBpbW1lZGlhdGVseSBvbiBl cnJvciBiZWxvdy4KCj4gKwo+ICsJZm9yICh0eXBlID0gMDsgdHlwZSA8IE1BWF9TRU5TT1JfVFlQ RTsgdHlwZSsrKSB7Cj4gKwkJaWYgKCFzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQpCj4g KwkJCWNvbnRpbnVlOwo+ICsKPiArCQlzZW5zb3JfZ3JvdXBzW3R5cGVdLmdyb3VwLmF0dHJzID0g ZGV2bV9remFsbG9jKCZwZGV2LT5kZXYsCj4gKwkJCQkJc2l6ZW9mKHN0cnVjdCBhdHRyaWJ1dGUq KSAqCj4gKwkJCQkJKHNlbnNvcl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCArIDEpLAo+ICsJCQkJ CUdGUF9LRVJORUwpOwo+ICsJCWlmICghc2Vuc29yX2dyb3Vwc1t0eXBlXS5ncm91cC5hdHRycykg ewo+ICsJCQlwcl9lcnIoIiVzOiBGYWlsZWQgdG8gYWxsb2NhdGUgbWVtb3J5IGZvciBhdHRyaWJ1 dGUiCj4gKwkJCQkJImFycmF5XG4iLCBfX2Z1bmNfXyk7CgpkZXZtX2t6YWxsb2MoKSBhbHJlYWR5 IGR1bXBzIGFuIGVycm9yIG1lc3NhZ2UuIFNhbWUgZm9yIGFsbCBvdGhlciBtZW1vcnkgZXJyb3Ig bWVzc2FnZXMuCgo+ICsJCQllcnIgPSAtRU5PTUVNOwo+ICsJCQlnb3RvIGV4aXRfcHV0X25vZGU7 Cj4gKwkJfQo+ICsKPiArCQlwZ3JvdXBzW3R5cGVdID0gJnNlbnNvcl9ncm91cHNbdHlwZV0uZ3Jv dXA7Cj4gKwkJcGRhdGEtPnNlbnNvcnNfY291bnQgKz0gc2Vuc29yX2dyb3Vwc1t0eXBlXS5hdHRy X2NvdW50Owo+ICsJCXNlbnNvcl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCA9IDA7Cj4gKwl9Cj4g Kwo+ICtleGl0X3B1dF9ub2RlOgo+ICsJb2Zfbm9kZV9wdXQob3BhbCk7Cj4gKwlyZXR1cm4gZXJy Owo+ICt9Cj4gKwo+ICsvKgo+ICsgKiBJdGVyYXRlIHRocm91Z2ggdGhlIGRldmljZSB0cmVlIGZv ciBlYWNoIGNoaWxkIG9mIHNlbnNvciBub2RlLCBjcmVhdGUKPiArICogYSBzeXNmcyBhdHRyaWJ1 dGUgZmlsZSwgdGhlIGZpbGUgaXMgbmFtZWQgYnkgdHJhbnNsYXRpbmcgdGhlIERUIG5vZGUgbmFt ZQo+ICsgKiB0byB0aGUgbmFtZSByZXF1aXJlZCBieSB0aGUgaGlnaGVyICdod21vbicgZHJpdmVy IGxpa2UgZmFuMV9pbnB1dCwgdGVtcDFfbWF4Cj4gKyAqIGV0Yy4uCj4gKyAqLwo+ICtzdGF0aWMg aW50IF9faW5pdCBjcmVhdGVfZGV2aWNlX2F0dHJzKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBk ZXYpCj4gK3sKPiArCXN0cnVjdCBwbGF0Zm9ybV9kYXRhICpwZGF0YSA9IHBsYXRmb3JtX2dldF9k cnZkYXRhKHBkZXYpOwo+ICsJY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqKnBncm91cHMg PSBwZGF0YS0+YXR0cl9ncm91cHM7Cj4gKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpucDsK PiArCXN0cnVjdCBzZW5zb3JfZGF0YSAqc2RhdGE7Cj4gKwljb25zdCB1MzIgKnNlbnNvcl9pZDsK PiArCWVudW0gc2Vuc29ycyB0eXBlOwo+ICsJdTMyIGNvdW50ID0gMDsKPiArCWludCBlcnIgPSAw Owo+ICsKPiArCW9wYWwgPSBvZl9maW5kX25vZGVfYnlfcGF0aCgiL2libSxvcGFsL3NlbnNvcnMi KTsKPiArICAgICAgICBpZiAoIW9wYWwpIHsKPiArCQlwcl9lcnIoIiVzOiBPcGFsICdzZW5zb3Jz JyBub2RlIG5vdCBmb3VuZFxuIiwgX19mdW5jX18pOwo+ICsJCXJldHVybiAtRU5PREVWOwo+ICsg ICAgICAgIH0KPiArCj4gKwlzZGF0YSA9IGRldm1fa3phbGxvYygmcGRldi0+ZGV2LCAocGRhdGEt PnNlbnNvcnNfY291bnQpICoKPiArCQkJICAgICBzaXplb2YoKnNkYXRhKSwgR0ZQX0tFUk5FTCk7 Cj4gKwlpZiAoIXNkYXRhKSB7Cj4gKwkJcHJfZXJyKCIlczogRmFpbGVkIHRvIGFsbG9jYXRlIG1l bW9yeSBmb3IgdGhlIHNlbnNvcl9kYXRhIiwKPiArCQkJCV9fZnVuY19fKTsKPiArCQllcnIgPSAt RU5PTUVNOwo+ICsJCWdvdG8gZXhpdF9wdXRfbm9kZTsKPiArCX0KPiArCj4gKwlmb3JfZWFjaF9j aGlsZF9vZl9ub2RlKG9wYWwsIG5wKSB7Cj4gKyAgICAgICAgICAgICAgICBpZiAobnAtPm5hbWUg PT0gTlVMTCkKPiArICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7Cj4gKwo+ICsJCWZv ciAodHlwZSA9IDA7IHR5cGUgPCBNQVhfU0VOU09SX1RZUEU7IHR5cGUrKykKPiArCQkJaWYgKG9m X2RldmljZV9pc19jb21wYXRpYmxlKG5wLAo+ICsJCQkJCXNlbnNvcl9ncm91cHNbdHlwZV0uY29t cGF0aWJsZSkpCj4gKwkJCQlicmVhazsKPiArCj4gKwkJaWYgKHR5cGUgPT0gTUFYX1NFTlNPUl9U WVBFKQo+ICsJCQljb250aW51ZTsKPiArCj4gKwkJc2Vuc29yX2lkID0gb2ZfZ2V0X3Byb3BlcnR5 KG5wLCAic2Vuc29yLWlkIiwgTlVMTCk7Cj4gKwkJaWYgKCFzZW5zb3JfaWQpIHsKPiArCQkJcHJf aW5mbygiJXM6ICVzIGRvZXNuJ3QgaGF2ZSBzZW5zb3ItaWRcbiIsIF9fZnVuY19fLAo+ICsJCQkJ bnAtPm5hbWUpOwo+ICsJCQljb250aW51ZTsKPiArCQl9Cj4gKwpDb25zaWRlciB1c2luZyBvZl9w cm9wZXJ0eV9yZWFkX3UzMigpLgoKPiArCQlzZGF0YVtjb3VudF0uaWQgPSAqc2Vuc29yX2lkOwo+ ICsJCXNkYXRhW2NvdW50XS50eXBlID0gdHlwZTsKPiArCQllcnIgPSBjcmVhdGVfaHdtb25fYXR0 cl9uYW1lKHR5cGUsIG5wLT5uYW1lLCBzZGF0YVtjb3VudF0ubmFtZSk7Cj4gKwkJaWYgKGVycikK PiArCQkJZ290byBleGl0X3B1dF9ub2RlOwo+ICsKPiArCQlzeXNmc19hdHRyX2luaXQoJnNkYXRh W2NvdW50XS5kZXZfYXR0ci5hdHRyKTsKPiArCQlzZGF0YVtjb3VudF0uZGV2X2F0dHIuYXR0ci5u YW1lID0gc2RhdGFbY291bnRdLm5hbWU7Cj4gKwkJc2RhdGFbY291bnRdLmRldl9hdHRyLmF0dHIu bW9kZSA9IFNfSVJVR087Cj4gKwkJc2RhdGFbY291bnRdLmRldl9hdHRyLnNob3cgPSBzaG93X3Nl bnNvcjsKPiArCj4gKwkJcGdyb3Vwc1t0eXBlXS0+YXR0cnNbc2Vuc29yX2dyb3Vwc1t0eXBlXS5h dHRyX2NvdW50KytdID0KPiArCQkJCSZzZGF0YVtjb3VudCsrXS5kZXZfYXR0ci5hdHRyOwo+ICsJ fQo+ICsKPiArZXhpdF9wdXRfbm9kZToKPiArCW9mX25vZGVfcHV0KG9wYWwpOwo+ICsJcmV0dXJu IGVycjsKPiArfQo+ICsKPiArc3RhdGljIGludCBfX2luaXQgaWJtcG93ZXJudl9wcm9iZShzdHJ1 Y3QgcGxhdGZvcm1fZGV2aWNlICpwZGV2KQo+ICt7Cj4gKwlzdHJ1Y3QgcGxhdGZvcm1fZGF0YSAq cGRhdGE7Cj4gKwlzdHJ1Y3QgZGV2aWNlICpod21vbl9kZXY7Cj4gKwlpbnQgZXJyOwo+ICsKPiAr CXBkYXRhID0gZGV2bV9remFsbG9jKCZwZGV2LT5kZXYsIHNpemVvZigqcGRhdGEpLCBHRlBfS0VS TkVMKTsKPiArCWlmICghcGRhdGEpCj4gKwkJcmV0dXJuIC1FTk9NRU07Cj4gKwo+ICsJcGxhdGZv cm1fc2V0X2RydmRhdGEocGRldiwgcGRhdGEpOwo+ICsJcGRhdGEtPnNlbnNvcnNfY291bnQgPSAw Owo+ICsJZXJyID0gcG9wdWxhdGVfYXR0cl9ncm91cHMocGRldik7Cj4gKwlpZiAoZXJyKQo+ICsJ CXJldHVybiBlcnI7Cj4gKwo+ICsJLyogQ3JlYXRlIHN5c2ZzIGF0dHJpYnV0ZSBmaWxlIGZvciBl YWNoIHNlbnNvciBmb3VuZCBpbiB0aGUgRFQgKi8KCkF0dHJpYnV0ZSBkYXRhLCBub3QgZmlsZQoK PiArCWVyciA9IGNyZWF0ZV9kZXZpY2VfYXR0cnMocGRldik7Cj4gKwlpZiAoZXJyKQo+ICsJCXJl dHVybiBlcnI7Cj4gKwo+ICsJLyogRmluYWxseSwgcmVnaXN0ZXIgd2l0aCBod21vbiAqLwo+ICsJ aHdtb25fZGV2ID0gZGV2bV9od21vbl9kZXZpY2VfcmVnaXN0ZXJfd2l0aF9ncm91cHMoJnBkZXYt PmRldiwgRFJWTkFNRSwKPiArCQkJCQkJCSAgIHBkYXRhLAo+ICsJCQkJCQkJICAgcGRhdGEtPmF0 dHJfZ3JvdXBzKTsKPiArCj4gKwlyZXR1cm4gUFRSX0VSUl9PUl9aRVJPKGh3bW9uX2Rldik7Cj4g K30KPiArCj4gK3N0YXRpYyBzdHJ1Y3QgcGxhdGZvcm1fZHJpdmVyIGlibXBvd2VybnZfZHJpdmVy ID0gewo+ICsJLmRyaXZlciA9IHsKPiArCQkub3duZXIgPSBUSElTX01PRFVMRSwKPiArCQkubmFt ZSA9IERSVk5BTUUsCj4gKwl9LAo+ICt9Owo+ICsKPiArc3RhdGljIGludCBfX2luaXQgaWJtcG93 ZXJudl9pbml0KHZvaWQpCj4gK3sKPiArCWludCBlcnI7Cj4gKwo+ICsJcGRldmljZSA9IHBsYXRm b3JtX2RldmljZV9hbGxvYyhEUlZOQU1FLCAwKTsKPiArCWlmICghcGRldmljZSkgewo+ICsJCXBy X2VycigiJXM6IERldmljZSBhbGxvY2F0aW9uIGZhaWxlZFxuIiwgX19mdW5jX18pOwo+ICsJCWVy ciA9IC1FTk9NRU07Cj4gKwkJZ290byBleGl0Owo+ICsJfQo+ICsKPiArCWVyciA9IHBsYXRmb3Jt X2RldmljZV9hZGQocGRldmljZSk7Cj4gKwlpZiAoZXJyKSB7Cj4gKwkJcHJfZXJyKCIlczogRGV2 aWNlIGFkZGl0aW9uIGZhaWxlZCAoJWQpXG4iLCBfX2Z1bmNfXywgZXJyKTsKPiArCQlnb3RvIGV4 aXRfZGV2aWNlX3B1dDsKPiArCX0KPiArCj4gKwllcnIgPSBwbGF0Zm9ybV9kcml2ZXJfcHJvYmUo JmlibXBvd2VybnZfZHJpdmVyLCBpYm1wb3dlcm52X3Byb2JlKTsKPiArCWlmIChlcnIpIHsKPiAr CQlwcl9lcnIoIiVzOiBQbGF0ZnJvbSBkcml2ZXIgcHJvYmUgZmFpbGVkXG4iLCBfX2Z1bmNfXyk7 Cj4gKwkJZ290byBleGl0X2RldmljZV9kZWw7Cj4gKwl9Cj4gKwo+ICsJcmV0dXJuIDA7Cj4gKwo+ ICtleGl0X2RldmljZV9kZWw6Cj4gKwlwbGF0Zm9ybV9kZXZpY2VfZGVsKHBkZXZpY2UpOwo+ICtl eGl0X2RldmljZV9wdXQ6Cj4gKwlwbGF0Zm9ybV9kZXZpY2VfcHV0KHBkZXZpY2UpOwo+ICtleGl0 Ogo+ICsJcmV0dXJuIGVycjsKPiArfQo+ICsKPiArc3RhdGljIHZvaWQgX19leGl0IGlibXBvd2Vy bnZfZXhpdCh2b2lkKQo+ICt7Cj4gKwlwbGF0Zm9ybV9kcml2ZXJfdW5yZWdpc3RlcigmaWJtcG93 ZXJudl9kcml2ZXIpOwo+ICsJcGxhdGZvcm1fZGV2aWNlX3VucmVnaXN0ZXIocGRldmljZSk7Cj4g K30KPiArCj4gK01PRFVMRV9BVVRIT1IoIk5lZWxlc2ggR3VwdGEgPG5lZWxlZ3VwQGxpbnV4LnZu ZXQuaWJtLmNvbT4iKTsKPiArTU9EVUxFX0RFU0NSSVBUSU9OKCJJQk0gUE9XRVJOViBwbGF0Zm9y bSBzZW5zb3JzIik7Cj4gK01PRFVMRV9MSUNFTlNFKCJHUEwiKTsKPiArCj4gK21vZHVsZV9pbml0 KGlibXBvd2VybnZfaW5pdCk7Cj4gK21vZHVsZV9leGl0KGlibXBvd2VybnZfZXhpdCk7Cj4KPgo+ CgoKX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX18KbG0tc2Vu c29ycyBtYWlsaW5nIGxpc3QKbG0tc2Vuc29yc0BsbS1zZW5zb3JzLm9yZwpodHRwOi8vbGlzdHMu bG0tc2Vuc29ycy5vcmcvbWFpbG1hbi9saXN0aW5mby9sbS1zZW5zb3Jz ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-28 7:23 ` Guenter Roeck 0 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-05-28 7:23 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 05/19/2014 07:26 AM, Neelesh Gupta wrote: > This patch adds basic kernel enablement for reading power values, fan > speed rpm and temperature values on powernv platforms which will > be exported to user space through sysfs interface. > > Test results: > ------------- > [root@tul163p1 ~]# sensors > ibmpowernv-isa-0000 > Adapter: ISA adapter > fan1: 5487 RPM (min = 0 RPM) > fan2: 5152 RPM (min = 0 RPM) > fan3: 5590 RPM (min = 0 RPM) > fan4: 4963 RPM (min = 0 RPM) > fan5: 0 RPM (min = 0 RPM) > fan6: 0 RPM (min = 0 RPM) > fan7: 7488 RPM (min = 0 RPM) > fan8: 7944 RPM (min = 0 RPM) > temp1: +39.0°C (high = +0.0°C) > power1: 192.00 W > > [root@tul163p1 ~]# ls /sys/devices/platform/ > alarmtimer ibmpowernv.0 rtc-generic serial8250 uevent > [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/ > driver/ hwmon/ modalias subsystem/ uevent > [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/hwmon/hwmon0/ > device fan2_min fan4_min fan6_min fan8_min power1_input > fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem > fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input > fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max > fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent > fan2_input fan4_input fan6_input fan8_input name > [root@tul163p1 ~]# > [root@tul163p1 ~]# ls /sys/class/hwmon/hwmon0/ > device fan2_min fan4_min fan6_min fan8_min power1_input > fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem > fan1_input fan3_input fan5_input fan7_input in2_fault temp1_input > fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max > fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent > fan2_input fan4_input fan6_input fan8_input name > [root@tul163p1 ~]# > The inX_fault attributes don't really make much sense. _fault attributes without _input attributes don't have any value and are, as you noticed, not displayed with the sensors command. Is this a problem in teh devicetree data or do you really have voltage faults without voltages ? > Signed-off-by: Neelesh Gupta <neelegup@linux.vnet.ibm.com> > --- > Checkpatch says: total: 8 errors, 11 warnings, 389 lines checked NOTE: whitespace errors detected, you may wish to use scripts/cleanpatch or scripts/cleanfile which should really not happen at this point. Please make sure you follow CodingStyle. checkpatch --strict points to a number of additional violations. More comments inline. > Changes in v2 > ============= > - Generic use of devm_* functions in hwmon like using devm_kzalloc() for dynamic > memory request, avoiding the need to explicit free of memory. > Adding 'struct attribute_group' as member of platform data structure to be > populated and then passed to devm_hwmon_device_register_with_groups(). > > Note: Having an array of pointers of 'attribute_group' and each group > corresponds to 'enum sensors' type. Not completely sure, if it's ideal or > could have just one group populated with attributes of sensor types? > Your call, really; whatever is easier for you. I won't dictate one or the other. Question though is what happens if one group is not populated. If I understand the code correctly this will result in the remaining groups to be 'dropped', ie not displayed at all. > - 'ibmpowernv' is not hot-pluggable device so moving 'platform_driver' callback > function (probe) as part of __init code. > - Fixed issues related to coding style. > - Other general comments in v1. > > drivers/hwmon/Kconfig | 8 + > drivers/hwmon/Makefile | 1 > drivers/hwmon/ibmpowernv.c | 368 ++++++++++++++++++++++++++++++++++++++++++++ You'll also need Documentation/hwmon/ibmpowernv and Documentation/devicetree/bindings/hwmon/ibmpowernv. The latter will need to get an Ack from the devicetree maintainers. > 3 files changed, 377 insertions(+) > create mode 100644 drivers/hwmon/ibmpowernv.c > > diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig > index bc196f4..3e308fa 100644 > --- a/drivers/hwmon/Kconfig > +++ b/drivers/hwmon/Kconfig > @@ -554,6 +554,14 @@ config SENSORS_IBMPEX > This driver can also be built as a module. If so, the module > will be called ibmpex. > > +config SENSORS_IBMPOWERNV > + tristate "IBM POWERNV platform sensors" > + depends on PPC_POWERNV > + default y > + help > + If you say yes here you get support for the temperature/fan/power > + sensors on your platform. > + > config SENSORS_IIO_HWMON > tristate "Hwmon driver that uses channels specified via iio maps" > depends on IIO > diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile > index c48f987..199c401 100644 > --- a/drivers/hwmon/Makefile > +++ b/drivers/hwmon/Makefile > @@ -71,6 +71,7 @@ obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o > obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o > obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o > obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o > +obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o > obj-$(CONFIG_SENSORS_IIO_HWMON) += iio_hwmon.o > obj-$(CONFIG_SENSORS_INA209) += ina209.o > obj-$(CONFIG_SENSORS_INA2XX) += ina2xx.o > diff --git a/drivers/hwmon/ibmpowernv.c b/drivers/hwmon/ibmpowernv.c > new file mode 100644 > index 0000000..afce620 > --- /dev/null > +++ b/drivers/hwmon/ibmpowernv.c > @@ -0,0 +1,368 @@ > +/* > + * IBM PowerNV platform sensors for temperature/fan/power > + * Copyright (C) 2014 IBM > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License as published by > + * the Free Software Foundation; either version 2 of the License, or > + * (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License > + * along with this program. > + */ > + > +#include <linux/init.h> > +#include <linux/module.h> > +#include <linux/kernel.h> > +#include <linux/hwmon.h> > +#include <linux/hwmon-sysfs.h> > +#include <linux/of.h> > +#include <linux/slab.h> > + > +#include <linux/platform_device.h> > +#include <asm/opal.h> > +#include <linux/err.h> > + > +#define DRVNAME "ibmpowernv" > +#define MAX_ATTR_LEN 32 > + > +/* Sensor suffix name from DT */ > +#define DT_FAULT_ATTR_SUFFIX "faulted" > +#define DT_DATA_ATTR_SUFFIX "data" > +#define DT_THRESHOLD_ATTR_SUFFIX "thrs" > + > +/* > + * Enumerates all the types of sensors in the POWERNV platform and does index > + * into 'struct sensor_group' > + */ > +enum sensors { > + FAN, > + AMBIENT_TEMP, > + POWER_SUPPLY, > + POWER_INPUT, > + MAX_SENSOR_TYPE, > +}; > + > +static struct sensor_group { > + const char *name; > + const char *compatible; > + struct attribute_group group; > + u32 attr_count; > +} sensor_groups[] = { > + {"fan", "ibm,opal-sensor-cooling-fan", {0}, 0}, > + {"temp", "ibm,opal-sensor-amb-temp", {0}, 0}, > + {"in", "ibm,opal-sensor-power-supply", {0}, 0}, > + {"power", "ibm,opal-sensor-power", {0}, 0} > +}; > + The '0' initializations should not be necessary. > +struct sensor_data { > + u32 id; /* An opaque id of the firmware for each sensor */ > + enum sensors type; > + char name[MAX_ATTR_LEN]; > + struct device_attribute dev_attr; > +}; > + > +struct platform_data { > + const struct attribute_group *attr_groups[MAX_SENSOR_TYPE + 1]; > + u32 sensors_count; /* Total count of sensors from each group */ > +}; > + > +/* Platform device representing all the ibmpowernv sensors */ > +static struct platform_device *pdevice; > + > +static ssize_t show_sensor(struct device *dev, struct device_attribute *devattr, > + char *buf) > +{ > + struct sensor_data *sdata = container_of(devattr, struct sensor_data, > + dev_attr); > + ssize_t ret; > + u32 x; > + > + ret = opal_get_sensor_data(sdata->id, &x); > + if (ret) { > + pr_err("%s: Failed to get opal sensor data\n", __func__); > + return ret; > + } > + > + /* Convert temperature to milli-degrees */ > + if (sdata->type == AMBIENT_TEMP) > + x *= 1000; > + /* Convert power to micro-watts */ > + else if (sdata->type == POWER_INPUT) > + x *= 1000000; > + > + return sprintf(buf, "%d\n", x); x is unsigned, so %u. > +} > + > +static void __init get_sensor_index_attr(const char *name, u32 *index, char *attr) > +{ > + char *hash_pos = strchr(name, '#'); > + char *dash_pos; > + u32 copy_len; > + char buf[8]; > + > + memset(buf, 0, sizeof(buf)); > + *index = 0; > + *attr = '\0'; > + > + if (hash_pos) { > + dash_pos = strchr(hash_pos, '-'); > + if (dash_pos) { > + copy_len = dash_pos - hash_pos - 1; > + if (copy_len < sizeof(buf)) { > + strncpy(buf, hash_pos + 1, copy_len); > + sscanf(buf, "%d", index); What if sscanf fails ? Might be an interesting exercise to try and create multiple sensors with index 0 (or, for that matter, with the same index value). Do you have any protection against bad input data ? Guess not; did you test what happens if you pass bad data to the driver (such as duplicate sensor entries) ? > + } > + > + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); > + } > + } > +} > + > +/* > + * This function translates the DT node name into the 'hwmon' attribute name. > + * IBMPOWERNV device node appear like cooling-fan#2-data, amb-temp#1-thrs etc. > + * which need to be mapped as fan2_input, temp1_max respectively before > + * populating them inside hwmon device class.. > + */ > +static int __init create_hwmon_attr_name(enum sensors type, const char *node_name, > + char *hwmon_attr_name) > +{ > + char attr_suffix[MAX_ATTR_LEN]; > + char *attr_name; > + u32 index; > + > + get_sensor_index_attr(node_name, &index, attr_suffix); > + if (!index || !strlen(attr_suffix)) { > + pr_info("%s: Sensor device node name is invalid, name: %s\n", > + __func__, node_name); > + return -EINVAL; > + } > + > + if (!strcmp(attr_suffix, DT_FAULT_ATTR_SUFFIX)) > + attr_name = "fault"; > + else if(!strcmp(attr_suffix, DT_DATA_ATTR_SUFFIX)) > + attr_name = "input"; > + else if (!strcmp(attr_suffix, DT_THRESHOLD_ATTR_SUFFIX)) { > + if (type == AMBIENT_TEMP) > + attr_name = "max"; > + else if (type == FAN) > + attr_name = "min"; > + else > + return -ENOENT; > + } else > + return -ENOENT; > + > + snprintf(hwmon_attr_name, MAX_ATTR_LEN, "%s%d_%s", > + sensor_groups[type].name, index, attr_name); > + return 0; > +} > + > +static int __init populate_attr_groups(struct platform_device *pdev) > +{ > + struct platform_data *pdata = platform_get_drvdata(pdev); > + const struct attribute_group **pgroups = pdata->attr_groups; > + struct device_node *opal, *np; > + enum sensors type; > + int err = 0; > + > + opal = of_find_node_by_path("/ibm,opal/sensors"); > + if (!opal) { An obvious whitespace error here. > + pr_err("%s: Opal 'sensors' node not found\n", __func__); > + return -ENODEV; > + } > + > + for_each_child_of_node(opal, np) { > + if (np->name == NULL) > + continue; > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) > + if (of_device_is_compatible(np, > + sensor_groups[type].compatible)) { > + sensor_groups[type].attr_count++; > + break; > + } > + } You should be able to do of_node_put(opal); here. Then you can return immediately on error below. > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) { > + if (!sensor_groups[type].attr_count) > + continue; > + > + sensor_groups[type].group.attrs = devm_kzalloc(&pdev->dev, > + sizeof(struct attribute*) * > + (sensor_groups[type].attr_count + 1), > + GFP_KERNEL); > + if (!sensor_groups[type].group.attrs) { > + pr_err("%s: Failed to allocate memory for attribute" > + "array\n", __func__); devm_kzalloc() already dumps an error message. Same for all other memory error messages. > + err = -ENOMEM; > + goto exit_put_node; > + } > + > + pgroups[type] = &sensor_groups[type].group; > + pdata->sensors_count += sensor_groups[type].attr_count; > + sensor_groups[type].attr_count = 0; > + } > + > +exit_put_node: > + of_node_put(opal); > + return err; > +} > + > +/* > + * Iterate through the device tree for each child of sensor node, create > + * a sysfs attribute file, the file is named by translating the DT node name > + * to the name required by the higher 'hwmon' driver like fan1_input, temp1_max > + * etc.. > + */ > +static int __init create_device_attrs(struct platform_device *pdev) > +{ > + struct platform_data *pdata = platform_get_drvdata(pdev); > + const struct attribute_group **pgroups = pdata->attr_groups; > + struct device_node *opal, *np; > + struct sensor_data *sdata; > + const u32 *sensor_id; > + enum sensors type; > + u32 count = 0; > + int err = 0; > + > + opal = of_find_node_by_path("/ibm,opal/sensors"); > + if (!opal) { > + pr_err("%s: Opal 'sensors' node not found\n", __func__); > + return -ENODEV; > + } > + > + sdata = devm_kzalloc(&pdev->dev, (pdata->sensors_count) * > + sizeof(*sdata), GFP_KERNEL); > + if (!sdata) { > + pr_err("%s: Failed to allocate memory for the sensor_data", > + __func__); > + err = -ENOMEM; > + goto exit_put_node; > + } > + > + for_each_child_of_node(opal, np) { > + if (np->name == NULL) > + continue; > + > + for (type = 0; type < MAX_SENSOR_TYPE; type++) > + if (of_device_is_compatible(np, > + sensor_groups[type].compatible)) > + break; > + > + if (type == MAX_SENSOR_TYPE) > + continue; > + > + sensor_id = of_get_property(np, "sensor-id", NULL); > + if (!sensor_id) { > + pr_info("%s: %s doesn't have sensor-id\n", __func__, > + np->name); > + continue; > + } > + Consider using of_property_read_u32(). > + sdata[count].id = *sensor_id; > + sdata[count].type = type; > + err = create_hwmon_attr_name(type, np->name, sdata[count].name); > + if (err) > + goto exit_put_node; > + > + sysfs_attr_init(&sdata[count].dev_attr.attr); > + sdata[count].dev_attr.attr.name = sdata[count].name; > + sdata[count].dev_attr.attr.mode = S_IRUGO; > + sdata[count].dev_attr.show = show_sensor; > + > + pgroups[type]->attrs[sensor_groups[type].attr_count++] = > + &sdata[count++].dev_attr.attr; > + } > + > +exit_put_node: > + of_node_put(opal); > + return err; > +} > + > +static int __init ibmpowernv_probe(struct platform_device *pdev) > +{ > + struct platform_data *pdata; > + struct device *hwmon_dev; > + int err; > + > + pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); > + if (!pdata) > + return -ENOMEM; > + > + platform_set_drvdata(pdev, pdata); > + pdata->sensors_count = 0; > + err = populate_attr_groups(pdev); > + if (err) > + return err; > + > + /* Create sysfs attribute file for each sensor found in the DT */ Attribute data, not file > + err = create_device_attrs(pdev); > + if (err) > + return err; > + > + /* Finally, register with hwmon */ > + hwmon_dev = devm_hwmon_device_register_with_groups(&pdev->dev, DRVNAME, > + pdata, > + pdata->attr_groups); > + > + return PTR_ERR_OR_ZERO(hwmon_dev); > +} > + > +static struct platform_driver ibmpowernv_driver = { > + .driver = { > + .owner = THIS_MODULE, > + .name = DRVNAME, > + }, > +}; > + > +static int __init ibmpowernv_init(void) > +{ > + int err; > + > + pdevice = platform_device_alloc(DRVNAME, 0); > + if (!pdevice) { > + pr_err("%s: Device allocation failed\n", __func__); > + err = -ENOMEM; > + goto exit; > + } > + > + err = platform_device_add(pdevice); > + if (err) { > + pr_err("%s: Device addition failed (%d)\n", __func__, err); > + goto exit_device_put; > + } > + > + err = platform_driver_probe(&ibmpowernv_driver, ibmpowernv_probe); > + if (err) { > + pr_err("%s: Platfrom driver probe failed\n", __func__); > + goto exit_device_del; > + } > + > + return 0; > + > +exit_device_del: > + platform_device_del(pdevice); > +exit_device_put: > + platform_device_put(pdevice); > +exit: > + return err; > +} > + > +static void __exit ibmpowernv_exit(void) > +{ > + platform_driver_unregister(&ibmpowernv_driver); > + platform_device_unregister(pdevice); > +} > + > +MODULE_AUTHOR("Neelesh Gupta <neelegup@linux.vnet.ibm.com>"); > +MODULE_DESCRIPTION("IBM POWERNV platform sensors"); > +MODULE_LICENSE("GPL"); > + > +module_init(ibmpowernv_init); > +module_exit(ibmpowernv_exit); > > > ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-28 7:23 ` Guenter Roeck @ 2014-05-28 7:41 ` Benjamin Herrenschmidt -1 siblings, 0 replies; 18+ messages in thread From: Benjamin Herrenschmidt @ 2014-05-28 7:41 UTC (permalink / raw) To: Guenter Roeck; +Cc: lm-sensors, sbhat, Neelesh Gupta, linuxppc-dev, jdelvare On Wed, 2014-05-28 at 00:23 -0700, Guenter Roeck wrote: > Consider using of_property_read_u32(). > > > + sdata[count].id = *sensor_id; > > + sdata[count].type = type; Especially since this is broken for Little Endian ! Neelesh, please make sure you test your patch on LE. Cheers, Ben. _______________________________________________ lm-sensors mailing list lm-sensors@lm-sensors.org http://lists.lm-sensors.org/mailman/listinfo/lm-sensors ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-28 7:41 ` Benjamin Herrenschmidt 0 siblings, 0 replies; 18+ messages in thread From: Benjamin Herrenschmidt @ 2014-05-28 7:41 UTC (permalink / raw) To: Guenter Roeck; +Cc: lm-sensors, sbhat, Neelesh Gupta, linuxppc-dev, jdelvare On Wed, 2014-05-28 at 00:23 -0700, Guenter Roeck wrote: > Consider using of_property_read_u32(). > > > + sdata[count].id = *sensor_id; > > + sdata[count].type = type; Especially since this is broken for Little Endian ! Neelesh, please make sure you test your patch on LE. Cheers, Ben. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-28 7:41 ` Benjamin Herrenschmidt @ 2014-05-30 14:17 ` Neelesh Gupta -1 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-30 14:05 UTC (permalink / raw) To: Benjamin Herrenschmidt, Guenter Roeck Cc: sbhat, linuxppc-dev, jdelvare, lm-sensors On 05/28/2014 01:11 PM, Benjamin Herrenschmidt wrote: > On Wed, 2014-05-28 at 00:23 -0700, Guenter Roeck wrote: >> Consider using of_property_read_u32(). >> >>> + sdata[count].id = *sensor_id; >>> + sdata[count].type = type; > Especially since this is broken for Little Endian ! > > Neelesh, please make sure you test your patch on LE. > > Cheers, > Ben. Fixing it and will surely test on LE as well before posting. - Neelesh ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-05-30 14:17 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-05-30 14:17 UTC (permalink / raw) To: Benjamin Herrenschmidt, Guenter Roeck Cc: sbhat, linuxppc-dev, jdelvare, lm-sensors On 05/28/2014 01:11 PM, Benjamin Herrenschmidt wrote: > On Wed, 2014-05-28 at 00:23 -0700, Guenter Roeck wrote: >> Consider using of_property_read_u32(). >> >>> + sdata[count].id = *sensor_id; >>> + sdata[count].type = type; > Especially since this is broken for Little Endian ! > > Neelesh, please make sure you test your patch on LE. > > Cheers, > Ben. Fixing it and will surely test on LE as well before posting. - Neelesh _______________________________________________ lm-sensors mailing list lm-sensors@lm-sensors.org http://lists.lm-sensors.org/mailman/listinfo/lm-sensors ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-28 7:23 ` Guenter Roeck @ 2014-06-09 8:27 ` Neelesh Gupta -1 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-06-09 8:15 UTC (permalink / raw) To: Guenter Roeck, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 05/28/2014 12:53 PM, Guenter Roeck wrote: > On 05/19/2014 07:26 AM, Neelesh Gupta wrote: >> This patch adds basic kernel enablement for reading power values, fan >> speed rpm and temperature values on powernv platforms which will >> be exported to user space through sysfs interface. >> >> Test results: >> ------------- >> [root@tul163p1 ~]# sensors >> ibmpowernv-isa-0000 >> Adapter: ISA adapter >> fan1: 5487 RPM (min = 0 RPM) >> fan2: 5152 RPM (min = 0 RPM) >> fan3: 5590 RPM (min = 0 RPM) >> fan4: 4963 RPM (min = 0 RPM) >> fan5: 0 RPM (min = 0 RPM) >> fan6: 0 RPM (min = 0 RPM) >> fan7: 7488 RPM (min = 0 RPM) >> fan8: 7944 RPM (min = 0 RPM) >> temp1: +39.0°C (high = +0.0°C) >> power1: 192.00 W >> >> [root@tul163p1 ~]# ls /sys/devices/platform/ >> alarmtimer ibmpowernv.0 rtc-generic serial8250 uevent >> [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/ >> driver/ hwmon/ modalias subsystem/ uevent >> [root@tul163p1 ~]# ls /sys/devices/platform/ibmpowernv.0/hwmon/hwmon0/ >> device fan2_min fan4_min fan6_min fan8_min power1_input >> fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem >> fan1_input fan3_input fan5_input fan7_input in2_fault >> temp1_input >> fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max >> fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent >> fan2_input fan4_input fan6_input fan8_input name >> [root@tul163p1 ~]# >> [root@tul163p1 ~]# ls /sys/class/hwmon/hwmon0/ >> device fan2_min fan4_min fan6_min fan8_min power1_input >> fan1_fault fan3_fault fan5_fault fan7_fault in1_fault subsystem >> fan1_input fan3_input fan5_input fan7_input in2_fault >> temp1_input >> fan1_min fan3_min fan5_min fan7_min in3_fault temp1_max >> fan2_fault fan4_fault fan6_fault fan8_fault in4_fault uevent >> fan2_input fan4_input fan6_input fan8_input name >> [root@tul163p1 ~]# >> > > > The inX_fault attributes don't really make much sense. _fault > attributes without > _input attributes don't have any value and are, as you noticed, not > displayed > with the sensors command. Is this a problem in teh devicetree data or > do you > really have voltage faults without voltages ? There is no issue with the device data, somehow I'm getting only the _fault attribute for the inX_ (power-supply) attributes. > >> Signed-off-by: Neelesh Gupta <neelegup@linux.vnet.ibm.com> >> --- >> > Checkpatch says: > > total: 8 errors, 11 warnings, 389 lines checked > > NOTE: whitespace errors detected, you may wish to use > scripts/cleanpatch or > scripts/cleanfile > > which should really not happen at this point. > > Please make sure you follow CodingStyle. checkpatch --strict points to > a number > of additional violations. > > More comments inline. Fixed all of these issues related to coding style. > >> Changes in v2 >> ============= >> - Generic use of devm_* functions in hwmon like using devm_kzalloc() >> for dynamic >> memory request, avoiding the need to explicit free of memory. >> Adding 'struct attribute_group' as member of platform data >> structure to be >> populated and then passed to >> devm_hwmon_device_register_with_groups(). >> >> Note: Having an array of pointers of 'attribute_group' and each group >> corresponds to 'enum sensors' type. Not completely sure, if it's >> ideal or >> could have just one group populated with attributes of sensor types? >> > Your call, really; whatever is easier for you. I won't dictate one or > the other. > > Question though is what happens if one group is not populated. If I > understand > the code correctly this will result in the remaining groups to be > 'dropped', > ie not displayed at all. Yes, should be fixed. > >> - 'ibmpowernv' is not hot-pluggable device so moving >> 'platform_driver' callback >> function (probe) as part of __init code. >> - Fixed issues related to coding style. >> - Other general comments in v1. >> >> drivers/hwmon/Kconfig | 8 + >> drivers/hwmon/Makefile | 1 >> drivers/hwmon/ibmpowernv.c | 368 >> ++++++++++++++++++++++++++++++++++++++++++++ > > You'll also need Documentation/hwmon/ibmpowernv and > Documentation/devicetree/bindings/hwmon/ibmpowernv. > > The latter will need to get an Ack from the devicetree maintainers. I'll do as required. >> 3 files changed, 377 insertions(+) >> create mode 100644 drivers/hwmon/ibmpowernv.c >> >> diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig >> index bc196f4..3e308fa 100644 >> --- a/drivers/hwmon/Kconfig >> +++ b/drivers/hwmon/Kconfig >> @@ -554,6 +554,14 @@ config SENSORS_IBMPEX >> This driver can also be built as a module. If so, the module >> will be called ibmpex. >> >> +config SENSORS_IBMPOWERNV >> + tristate "IBM POWERNV platform sensors" >> + depends on PPC_POWERNV >> + default y >> + help >> + If you say yes here you get support for the temperature/fan/power >> + sensors on your platform. >> + >> config SENSORS_IIO_HWMON >> tristate "Hwmon driver that uses channels specified via iio maps" >> depends on IIO >> diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile >> index c48f987..199c401 100644 >> --- a/drivers/hwmon/Makefile >> +++ b/drivers/hwmon/Makefile >> @@ -71,6 +71,7 @@ obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o >> obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o >> obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o >> obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o >> +obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o >> obj-$(CONFIG_SENSORS_IIO_HWMON) += iio_hwmon.o >> obj-$(CONFIG_SENSORS_INA209) += ina209.o >> obj-$(CONFIG_SENSORS_INA2XX) += ina2xx.o >> diff --git a/drivers/hwmon/ibmpowernv.c b/drivers/hwmon/ibmpowernv.c >> new file mode 100644 >> index 0000000..afce620 >> --- /dev/null >> +++ b/drivers/hwmon/ibmpowernv.c >> @@ -0,0 +1,368 @@ >> +/* >> + * IBM PowerNV platform sensors for temperature/fan/power >> + * Copyright (C) 2014 IBM >> + * >> + * This program is free software; you can redistribute it and/or modify >> + * it under the terms of the GNU General Public License as published by >> + * the Free Software Foundation; either version 2 of the License, or >> + * (at your option) any later version. >> + * >> + * This program is distributed in the hope that it will be useful, >> + * but WITHOUT ANY WARRANTY; without even the implied warranty of >> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the >> + * GNU General Public License for more details. >> + * >> + * You should have received a copy of the GNU General Public License >> + * along with this program. >> + */ >> + >> +#include <linux/init.h> >> +#include <linux/module.h> >> +#include <linux/kernel.h> >> +#include <linux/hwmon.h> >> +#include <linux/hwmon-sysfs.h> >> +#include <linux/of.h> >> +#include <linux/slab.h> >> + >> +#include <linux/platform_device.h> >> +#include <asm/opal.h> >> +#include <linux/err.h> >> + >> +#define DRVNAME "ibmpowernv" >> +#define MAX_ATTR_LEN 32 >> + >> +/* Sensor suffix name from DT */ >> +#define DT_FAULT_ATTR_SUFFIX "faulted" >> +#define DT_DATA_ATTR_SUFFIX "data" >> +#define DT_THRESHOLD_ATTR_SUFFIX "thrs" >> + >> +/* >> + * Enumerates all the types of sensors in the POWERNV platform and >> does index >> + * into 'struct sensor_group' >> + */ >> +enum sensors { >> + FAN, >> + AMBIENT_TEMP, >> + POWER_SUPPLY, >> + POWER_INPUT, >> + MAX_SENSOR_TYPE, >> +}; >> + >> +static struct sensor_group { >> + const char *name; >> + const char *compatible; >> + struct attribute_group group; >> + u32 attr_count; >> +} sensor_groups[] = { >> + {"fan", "ibm,opal-sensor-cooling-fan", {0}, 0}, >> + {"temp", "ibm,opal-sensor-amb-temp", {0}, 0}, >> + {"in", "ibm,opal-sensor-power-supply", {0}, 0}, >> + {"power", "ibm,opal-sensor-power", {0}, 0} >> +}; >> + > The '0' initializations should not be necessary. > > >> +struct sensor_data { >> + u32 id; /* An opaque id of the firmware for each sensor */ >> + enum sensors type; >> + char name[MAX_ATTR_LEN]; >> + struct device_attribute dev_attr; >> +}; >> + >> +struct platform_data { >> + const struct attribute_group *attr_groups[MAX_SENSOR_TYPE + 1]; >> + u32 sensors_count; /* Total count of sensors from each group */ >> +}; >> + >> +/* Platform device representing all the ibmpowernv sensors */ >> +static struct platform_device *pdevice; >> + >> +static ssize_t show_sensor(struct device *dev, struct >> device_attribute *devattr, >> + char *buf) >> +{ >> + struct sensor_data *sdata = container_of(devattr, struct >> sensor_data, >> + dev_attr); >> + ssize_t ret; >> + u32 x; >> + >> + ret = opal_get_sensor_data(sdata->id, &x); >> + if (ret) { >> + pr_err("%s: Failed to get opal sensor data\n", __func__); >> + return ret; >> + } >> + >> + /* Convert temperature to milli-degrees */ >> + if (sdata->type == AMBIENT_TEMP) >> + x *= 1000; >> + /* Convert power to micro-watts */ >> + else if (sdata->type == POWER_INPUT) >> + x *= 1000000; >> + >> + return sprintf(buf, "%d\n", x); > > x is unsigned, so %u. Done. > >> +} >> + >> +static void __init get_sensor_index_attr(const char *name, u32 >> *index, char *attr) >> +{ >> + char *hash_pos = strchr(name, '#'); >> + char *dash_pos; >> + u32 copy_len; >> + char buf[8]; >> + >> + memset(buf, 0, sizeof(buf)); >> + *index = 0; >> + *attr = '\0'; >> + >> + if (hash_pos) { >> + dash_pos = strchr(hash_pos, '-'); >> + if (dash_pos) { >> + copy_len = dash_pos - hash_pos - 1; >> + if (copy_len < sizeof(buf)) { >> + strncpy(buf, hash_pos + 1, copy_len); >> + sscanf(buf, "%d", index); > > What if sscanf fails ? Might be an interesting exercise to try and create > multiple sensors with index 0 (or, for that matter, with the same > index value). > Do you have any protection against bad input data ? Guess not; did you > test > what happens if you pass bad data to the driver (such as duplicate sensor > entries) ? Well, rewriting this function to return the error code if fails. Next version will cover these test cases covered. Thanks. > >> + } >> + >> + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); >> + } >> + } >> +} >> + >> +/* >> + * This function translates the DT node name into the 'hwmon' >> attribute name. >> + * IBMPOWERNV device node appear like cooling-fan#2-data, >> amb-temp#1-thrs etc. >> + * which need to be mapped as fan2_input, temp1_max respectively before >> + * populating them inside hwmon device class.. >> + */ >> +static int __init create_hwmon_attr_name(enum sensors type, const >> char *node_name, >> + char *hwmon_attr_name) >> +{ >> + char attr_suffix[MAX_ATTR_LEN]; >> + char *attr_name; >> + u32 index; >> + >> + get_sensor_index_attr(node_name, &index, attr_suffix); >> + if (!index || !strlen(attr_suffix)) { >> + pr_info("%s: Sensor device node name is invalid, name: %s\n", >> + __func__, node_name); >> + return -EINVAL; >> + } >> + >> + if (!strcmp(attr_suffix, DT_FAULT_ATTR_SUFFIX)) >> + attr_name = "fault"; >> + else if(!strcmp(attr_suffix, DT_DATA_ATTR_SUFFIX)) >> + attr_name = "input"; >> + else if (!strcmp(attr_suffix, DT_THRESHOLD_ATTR_SUFFIX)) { >> + if (type == AMBIENT_TEMP) >> + attr_name = "max"; >> + else if (type == FAN) >> + attr_name = "min"; >> + else >> + return -ENOENT; >> + } else >> + return -ENOENT; >> + >> + snprintf(hwmon_attr_name, MAX_ATTR_LEN, "%s%d_%s", >> + sensor_groups[type].name, index, attr_name); >> + return 0; >> +} >> + >> +static int __init populate_attr_groups(struct platform_device *pdev) >> +{ >> + struct platform_data *pdata = platform_get_drvdata(pdev); >> + const struct attribute_group **pgroups = pdata->attr_groups; >> + struct device_node *opal, *np; >> + enum sensors type; >> + int err = 0; >> + >> + opal = of_find_node_by_path("/ibm,opal/sensors"); >> + if (!opal) { > > An obvious whitespace error here. > >> + pr_err("%s: Opal 'sensors' node not found\n", __func__); >> + return -ENODEV; >> + } >> + >> + for_each_child_of_node(opal, np) { >> + if (np->name == NULL) >> + continue; >> + >> + for (type = 0; type < MAX_SENSOR_TYPE; type++) >> + if (of_device_is_compatible(np, >> + sensor_groups[type].compatible)) { >> + sensor_groups[type].attr_count++; >> + break; >> + } >> + } > > You should be able to do > of_node_put(opal); > > here. Then you can return immediately on error below. Done. > >> + >> + for (type = 0; type < MAX_SENSOR_TYPE; type++) { >> + if (!sensor_groups[type].attr_count) >> + continue; >> + >> + sensor_groups[type].group.attrs = devm_kzalloc(&pdev->dev, >> + sizeof(struct attribute*) * >> + (sensor_groups[type].attr_count + 1), >> + GFP_KERNEL); >> + if (!sensor_groups[type].group.attrs) { >> + pr_err("%s: Failed to allocate memory for attribute" >> + "array\n", __func__); > > devm_kzalloc() already dumps an error message. Same for all other > memory error messages. > >> + err = -ENOMEM; >> + goto exit_put_node; >> + } >> + >> + pgroups[type] = &sensor_groups[type].group; >> + pdata->sensors_count += sensor_groups[type].attr_count; >> + sensor_groups[type].attr_count = 0; >> + } >> + >> +exit_put_node: >> + of_node_put(opal); >> + return err; >> +} >> + >> +/* >> + * Iterate through the device tree for each child of sensor node, >> create >> + * a sysfs attribute file, the file is named by translating the DT >> node name >> + * to the name required by the higher 'hwmon' driver like >> fan1_input, temp1_max >> + * etc.. >> + */ >> +static int __init create_device_attrs(struct platform_device *pdev) >> +{ >> + struct platform_data *pdata = platform_get_drvdata(pdev); >> + const struct attribute_group **pgroups = pdata->attr_groups; >> + struct device_node *opal, *np; >> + struct sensor_data *sdata; >> + const u32 *sensor_id; >> + enum sensors type; >> + u32 count = 0; >> + int err = 0; >> + >> + opal = of_find_node_by_path("/ibm,opal/sensors"); >> + if (!opal) { >> + pr_err("%s: Opal 'sensors' node not found\n", __func__); >> + return -ENODEV; >> + } >> + >> + sdata = devm_kzalloc(&pdev->dev, (pdata->sensors_count) * >> + sizeof(*sdata), GFP_KERNEL); >> + if (!sdata) { >> + pr_err("%s: Failed to allocate memory for the sensor_data", >> + __func__); >> + err = -ENOMEM; >> + goto exit_put_node; >> + } >> + >> + for_each_child_of_node(opal, np) { >> + if (np->name == NULL) >> + continue; >> + >> + for (type = 0; type < MAX_SENSOR_TYPE; type++) >> + if (of_device_is_compatible(np, >> + sensor_groups[type].compatible)) >> + break; >> + >> + if (type == MAX_SENSOR_TYPE) >> + continue; >> + >> + sensor_id = of_get_property(np, "sensor-id", NULL); >> + if (!sensor_id) { >> + pr_info("%s: %s doesn't have sensor-id\n", __func__, >> + np->name); >> + continue; >> + } >> + > Consider using of_property_read_u32(). Okay. > >> + sdata[count].id = *sensor_id; >> + sdata[count].type = type; >> + err = create_hwmon_attr_name(type, np->name, >> sdata[count].name); >> + if (err) >> + goto exit_put_node; >> + >> + sysfs_attr_init(&sdata[count].dev_attr.attr); >> + sdata[count].dev_attr.attr.name = sdata[count].name; >> + sdata[count].dev_attr.attr.mode = S_IRUGO; >> + sdata[count].dev_attr.show = show_sensor; >> + >> + pgroups[type]->attrs[sensor_groups[type].attr_count++] = >> + &sdata[count++].dev_attr.attr; >> + } >> + >> +exit_put_node: >> + of_node_put(opal); >> + return err; >> +} >> + >> +static int __init ibmpowernv_probe(struct platform_device *pdev) >> +{ >> + struct platform_data *pdata; >> + struct device *hwmon_dev; >> + int err; >> + >> + pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); >> + if (!pdata) >> + return -ENOMEM; >> + >> + platform_set_drvdata(pdev, pdata); >> + pdata->sensors_count = 0; >> + err = populate_attr_groups(pdev); >> + if (err) >> + return err; >> + >> + /* Create sysfs attribute file for each sensor found in the DT */ > > Attribute data, not file > >> + err = create_device_attrs(pdev); >> + if (err) >> + return err; >> + >> + /* Finally, register with hwmon */ >> + hwmon_dev = devm_hwmon_device_register_with_groups(&pdev->dev, >> DRVNAME, >> + pdata, >> + pdata->attr_groups); >> + >> + return PTR_ERR_OR_ZERO(hwmon_dev); >> +} >> + >> +static struct platform_driver ibmpowernv_driver = { >> + .driver = { >> + .owner = THIS_MODULE, >> + .name = DRVNAME, >> + }, >> +}; >> + >> +static int __init ibmpowernv_init(void) >> +{ >> + int err; >> + >> + pdevice = platform_device_alloc(DRVNAME, 0); >> + if (!pdevice) { >> + pr_err("%s: Device allocation failed\n", __func__); >> + err = -ENOMEM; >> + goto exit; >> + } >> + >> + err = platform_device_add(pdevice); >> + if (err) { >> + pr_err("%s: Device addition failed (%d)\n", __func__, err); >> + goto exit_device_put; >> + } >> + >> + err = platform_driver_probe(&ibmpowernv_driver, ibmpowernv_probe); >> + if (err) { >> + pr_err("%s: Platfrom driver probe failed\n", __func__); >> + goto exit_device_del; >> + } >> + >> + return 0; >> + >> +exit_device_del: >> + platform_device_del(pdevice); >> +exit_device_put: >> + platform_device_put(pdevice); >> +exit: >> + return err; >> +} >> + >> +static void __exit ibmpowernv_exit(void) >> +{ >> + platform_driver_unregister(&ibmpowernv_driver); >> + platform_device_unregister(pdevice); >> +} >> + >> +MODULE_AUTHOR("Neelesh Gupta <neelegup@linux.vnet.ibm.com>"); >> +MODULE_DESCRIPTION("IBM POWERNV platform sensors"); >> +MODULE_LICENSE("GPL"); >> + >> +module_init(ibmpowernv_init); >> +module_exit(ibmpowernv_exit); >> >> >> > ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-06-09 8:27 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-06-09 8:27 UTC (permalink / raw) To: Guenter Roeck, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat Ck9uIDA1LzI4LzIwMTQgMTI6NTMgUE0sIEd1ZW50ZXIgUm9lY2sgd3JvdGU6Cj4gT24gMDUvMTkv MjAxNCAwNzoyNiBBTSwgTmVlbGVzaCBHdXB0YSB3cm90ZToKPj4gVGhpcyBwYXRjaCBhZGRzIGJh c2ljIGtlcm5lbCBlbmFibGVtZW50IGZvciByZWFkaW5nIHBvd2VyIHZhbHVlcywgZmFuCj4+IHNw ZWVkIHJwbSBhbmQgdGVtcGVyYXR1cmUgdmFsdWVzIG9uIHBvd2VybnYgcGxhdGZvcm1zIHdoaWNo IHdpbGwKPj4gYmUgZXhwb3J0ZWQgdG8gdXNlciBzcGFjZSB0aHJvdWdoIHN5c2ZzIGludGVyZmFj ZS4KPj4KPj4gVGVzdCByZXN1bHRzOgo+PiAtLS0tLS0tLS0tLS0tCj4+IFtyb290QHR1bDE2M3Ax IH5dIyBzZW5zb3JzCj4+IGlibXBvd2VybnYtaXNhLTAwMDAKPj4gQWRhcHRlcjogSVNBIGFkYXB0 ZXIKPj4gZmFuMTogICAgICAgIDU0ODcgUlBNICAobWluID0gICAgMCBSUE0pCj4+IGZhbjI6ICAg ICAgICA1MTUyIFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+PiBmYW4zOiAgICAgICAgNTU5MCBSUE0g IChtaW4gPSAgICAwIFJQTSkKPj4gZmFuNDogICAgICAgIDQ5NjMgUlBNICAobWluID0gICAgMCBS UE0pCj4+IGZhbjU6ICAgICAgICAgICAwIFJQTSAgKG1pbiA9ICAgIDAgUlBNKQo+PiBmYW42OiAg ICAgICAgICAgMCBSUE0gIChtaW4gPSAgICAwIFJQTSkKPj4gZmFuNzogICAgICAgIDc0ODggUlBN ICAobWluID0gICAgMCBSUE0pCj4+IGZhbjg6ICAgICAgICA3OTQ0IFJQTSAgKG1pbiA9ICAgIDAg UlBNKQo+PiB0ZW1wMTogICAgICAgICszOS4wwrBDICAoaGlnaCA9ICArMC4wwrBDKQo+PiBwb3dl cjE6ICAgICAgMTkyLjAwIFcKPj4KPj4gW3Jvb3RAdHVsMTYzcDEgfl0jIGxzIC9zeXMvZGV2aWNl cy9wbGF0Zm9ybS8KPj4gYWxhcm10aW1lciAgaWJtcG93ZXJudi4wICBydGMtZ2VuZXJpYyAgc2Vy aWFsODI1MCAgdWV2ZW50Cj4+IFtyb290QHR1bDE2M3AxIH5dIyBscyAvc3lzL2RldmljZXMvcGxh dGZvcm0vaWJtcG93ZXJudi4wLwo+PiBkcml2ZXIvICAgIGh3bW9uLyAgICAgbW9kYWxpYXMgICBz dWJzeXN0ZW0vIHVldmVudAo+PiBbcm9vdEB0dWwxNjNwMSB+XSMgbHMgL3N5cy9kZXZpY2VzL3Bs YXRmb3JtL2libXBvd2VybnYuMC9od21vbi9od21vbjAvCj4+IGRldmljZSAgICAgICAgZmFuMl9t aW4gICAgZmFuNF9taW4gICAgZmFuNl9taW4gICAgZmFuOF9taW4gcG93ZXIxX2lucHV0Cj4+IGZh bjFfZmF1bHQgIGZhbjNfZmF1bHQgICAgZmFuNV9mYXVsdCAgZmFuN19mYXVsdCAgICBpbjFfZmF1 bHQgc3Vic3lzdGVtCj4+IGZhbjFfaW5wdXQgIGZhbjNfaW5wdXQgICAgZmFuNV9pbnB1dCAgZmFu N19pbnB1dCAgICBpbjJfZmF1bHQgCj4+IHRlbXAxX2lucHV0Cj4+IGZhbjFfbWluICAgIGZhbjNf bWluICAgIGZhbjVfbWluICAgIGZhbjdfbWluICAgIGluM19mYXVsdCB0ZW1wMV9tYXgKPj4gZmFu Ml9mYXVsdCAgZmFuNF9mYXVsdCAgICBmYW42X2ZhdWx0ICBmYW44X2ZhdWx0ICAgIGluNF9mYXVs dCB1ZXZlbnQKPj4gZmFuMl9pbnB1dCAgZmFuNF9pbnB1dCAgICBmYW42X2lucHV0ICBmYW44X2lu cHV0ICAgIG5hbWUKPj4gW3Jvb3RAdHVsMTYzcDEgfl0jCj4+IFtyb290QHR1bDE2M3AxIH5dIyBs cyAvc3lzL2NsYXNzL2h3bW9uL2h3bW9uMC8KPj4gZGV2aWNlICAgICAgICBmYW4yX21pbiAgICBm YW40X21pbiAgICBmYW42X21pbiAgICBmYW44X21pbiBwb3dlcjFfaW5wdXQKPj4gZmFuMV9mYXVs dCAgZmFuM19mYXVsdCAgICBmYW41X2ZhdWx0ICBmYW43X2ZhdWx0ICAgIGluMV9mYXVsdCBzdWJz eXN0ZW0KPj4gZmFuMV9pbnB1dCAgZmFuM19pbnB1dCAgICBmYW41X2lucHV0ICBmYW43X2lucHV0 ICAgIGluMl9mYXVsdCAKPj4gdGVtcDFfaW5wdXQKPj4gZmFuMV9taW4gICAgZmFuM19taW4gICAg ZmFuNV9taW4gICAgZmFuN19taW4gICAgaW4zX2ZhdWx0IHRlbXAxX21heAo+PiBmYW4yX2ZhdWx0 ICBmYW40X2ZhdWx0ICAgIGZhbjZfZmF1bHQgIGZhbjhfZmF1bHQgICAgaW40X2ZhdWx0IHVldmVu dAo+PiBmYW4yX2lucHV0ICBmYW40X2lucHV0ICAgIGZhbjZfaW5wdXQgIGZhbjhfaW5wdXQgICAg bmFtZQo+PiBbcm9vdEB0dWwxNjNwMSB+XSMKPj4KPgo+Cj4gVGhlIGluWF9mYXVsdCBhdHRyaWJ1 dGVzIGRvbid0IHJlYWxseSBtYWtlIG11Y2ggc2Vuc2UuIF9mYXVsdCAKPiBhdHRyaWJ1dGVzIHdp dGhvdXQKPiBfaW5wdXQgYXR0cmlidXRlcyBkb24ndCBoYXZlIGFueSB2YWx1ZSBhbmQgYXJlLCBh cyB5b3Ugbm90aWNlZCwgbm90IAo+IGRpc3BsYXllZAo+IHdpdGggdGhlIHNlbnNvcnMgY29tbWFu ZC4gSXMgdGhpcyBhIHByb2JsZW0gaW4gdGVoIGRldmljZXRyZWUgZGF0YSBvciAKPiBkbyB5b3UK PiByZWFsbHkgaGF2ZSB2b2x0YWdlIGZhdWx0cyB3aXRob3V0IHZvbHRhZ2VzID8KClRoZXJlIGlz IG5vIGlzc3VlIHdpdGggdGhlIGRldmljZSBkYXRhLCBzb21laG93IEknbSBnZXR0aW5nIG9ubHkg dGhlIApfZmF1bHQgYXR0cmlidXRlCmZvciB0aGUgaW5YXyAocG93ZXItc3VwcGx5KSBhdHRyaWJ1 dGVzLgoKPgo+PiBTaWduZWQtb2ZmLWJ5OiBOZWVsZXNoIEd1cHRhIDxuZWVsZWd1cEBsaW51eC52 bmV0LmlibS5jb20+Cj4+IC0tLQo+Pgo+IENoZWNrcGF0Y2ggc2F5czoKPgo+IHRvdGFsOiA4IGVy cm9ycywgMTEgd2FybmluZ3MsIDM4OSBsaW5lcyBjaGVja2VkCj4KPiBOT1RFOiB3aGl0ZXNwYWNl IGVycm9ycyBkZXRlY3RlZCwgeW91IG1heSB3aXNoIHRvIHVzZSAKPiBzY3JpcHRzL2NsZWFucGF0 Y2ggb3IKPiAgICAgICBzY3JpcHRzL2NsZWFuZmlsZQo+Cj4gd2hpY2ggc2hvdWxkIHJlYWxseSBu b3QgaGFwcGVuIGF0IHRoaXMgcG9pbnQuCj4KPiBQbGVhc2UgbWFrZSBzdXJlIHlvdSBmb2xsb3cg Q29kaW5nU3R5bGUuIGNoZWNrcGF0Y2ggLS1zdHJpY3QgcG9pbnRzIHRvIAo+IGEgbnVtYmVyCj4g b2YgYWRkaXRpb25hbCB2aW9sYXRpb25zLgo+Cj4gTW9yZSBjb21tZW50cyBpbmxpbmUuCgpGaXhl ZCBhbGwgb2YgdGhlc2UgaXNzdWVzIHJlbGF0ZWQgdG8gY29kaW5nIHN0eWxlLgoKPgo+PiBDaGFu Z2VzIGluIHYyCj4+ID09PT09PT09PT09PT0KPj4gLSBHZW5lcmljIHVzZSBvZiBkZXZtXyogZnVu Y3Rpb25zIGluIGh3bW9uIGxpa2UgdXNpbmcgZGV2bV9remFsbG9jKCkgCj4+IGZvciBkeW5hbWlj Cj4+ICAgIG1lbW9yeSByZXF1ZXN0LCBhdm9pZGluZyB0aGUgbmVlZCB0byBleHBsaWNpdCBmcmVl IG9mIG1lbW9yeS4KPj4gICAgQWRkaW5nICdzdHJ1Y3QgYXR0cmlidXRlX2dyb3VwJyBhcyBtZW1i ZXIgb2YgcGxhdGZvcm0gZGF0YSAKPj4gc3RydWN0dXJlIHRvIGJlCj4+ICAgIHBvcHVsYXRlZCBh bmQgdGhlbiBwYXNzZWQgdG8gCj4+IGRldm1faHdtb25fZGV2aWNlX3JlZ2lzdGVyX3dpdGhfZ3Jv dXBzKCkuCj4+Cj4+ICAgIE5vdGU6IEhhdmluZyBhbiBhcnJheSBvZiBwb2ludGVycyBvZiAnYXR0 cmlidXRlX2dyb3VwJyBhbmQgZWFjaCBncm91cAo+PiAgICBjb3JyZXNwb25kcyB0byAnZW51bSBz ZW5zb3JzJyB0eXBlLiBOb3QgY29tcGxldGVseSBzdXJlLCBpZiBpdCdzIAo+PiBpZGVhbCBvcgo+ PiAgICBjb3VsZCBoYXZlIGp1c3Qgb25lIGdyb3VwIHBvcHVsYXRlZCB3aXRoIGF0dHJpYnV0ZXMg b2Ygc2Vuc29yIHR5cGVzPwo+Pgo+IFlvdXIgY2FsbCwgcmVhbGx5OyB3aGF0ZXZlciBpcyBlYXNp ZXIgZm9yIHlvdS4gSSB3b24ndCBkaWN0YXRlIG9uZSBvciAKPiB0aGUgb3RoZXIuCj4KPiBRdWVz dGlvbiB0aG91Z2ggaXMgd2hhdCBoYXBwZW5zIGlmIG9uZSBncm91cCBpcyBub3QgcG9wdWxhdGVk LiBJZiBJIAo+IHVuZGVyc3RhbmQKPiB0aGUgY29kZSBjb3JyZWN0bHkgdGhpcyB3aWxsIHJlc3Vs dCBpbiB0aGUgcmVtYWluaW5nIGdyb3VwcyB0byBiZSAKPiAnZHJvcHBlZCcsCj4gaWUgbm90IGRp c3BsYXllZCBhdCBhbGwuCgpZZXMsIHNob3VsZCBiZSBmaXhlZC4KCj4KPj4gLSAnaWJtcG93ZXJu dicgaXMgbm90IGhvdC1wbHVnZ2FibGUgZGV2aWNlIHNvIG1vdmluZyAKPj4gJ3BsYXRmb3JtX2Ry aXZlcicgY2FsbGJhY2sKPj4gICAgZnVuY3Rpb24gKHByb2JlKSBhcyBwYXJ0IG9mIF9faW5pdCBj b2RlLgo+PiAtIEZpeGVkIGlzc3VlcyByZWxhdGVkIHRvIGNvZGluZyBzdHlsZS4KPj4gLSBPdGhl ciBnZW5lcmFsIGNvbW1lbnRzIGluIHYxLgo+Pgo+PiAgIGRyaXZlcnMvaHdtb24vS2NvbmZpZyAg ICAgIHwgICAgOCArCj4+ICAgZHJpdmVycy9od21vbi9NYWtlZmlsZSAgICAgfCAgICAxCj4+ICAg ZHJpdmVycy9od21vbi9pYm1wb3dlcm52LmMgfCAgMzY4IAo+PiArKysrKysrKysrKysrKysrKysr KysrKysrKysrKysrKysrKysrKysrKysrKwo+Cj4gWW91J2xsIGFsc28gbmVlZCBEb2N1bWVudGF0 aW9uL2h3bW9uL2libXBvd2VybnYgYW5kCj4gRG9jdW1lbnRhdGlvbi9kZXZpY2V0cmVlL2JpbmRp bmdzL2h3bW9uL2libXBvd2VybnYuCj4KPiBUaGUgbGF0dGVyIHdpbGwgbmVlZCB0byBnZXQgYW4g QWNrIGZyb20gdGhlIGRldmljZXRyZWUgbWFpbnRhaW5lcnMuCgpJJ2xsIGRvIGFzIHJlcXVpcmVk LgoKPj4gICAzIGZpbGVzIGNoYW5nZWQsIDM3NyBpbnNlcnRpb25zKCspCj4+ICAgY3JlYXRlIG1v ZGUgMTAwNjQ0IGRyaXZlcnMvaHdtb24vaWJtcG93ZXJudi5jCj4+Cj4+IGRpZmYgLS1naXQgYS9k cml2ZXJzL2h3bW9uL0tjb25maWcgYi9kcml2ZXJzL2h3bW9uL0tjb25maWcKPj4gaW5kZXggYmMx OTZmNC4uM2UzMDhmYSAxMDA2NDQKPj4gLS0tIGEvZHJpdmVycy9od21vbi9LY29uZmlnCj4+ICsr KyBiL2RyaXZlcnMvaHdtb24vS2NvbmZpZwo+PiBAQCAtNTU0LDYgKzU1NCwxNCBAQCBjb25maWcg U0VOU09SU19JQk1QRVgKPj4gICAgICAgICBUaGlzIGRyaXZlciBjYW4gYWxzbyBiZSBidWlsdCBh cyBhIG1vZHVsZS4gIElmIHNvLCB0aGUgbW9kdWxlCj4+ICAgICAgICAgd2lsbCBiZSBjYWxsZWQg aWJtcGV4Lgo+Pgo+PiArY29uZmlnIFNFTlNPUlNfSUJNUE9XRVJOVgo+PiArICAgIHRyaXN0YXRl ICJJQk0gUE9XRVJOViBwbGF0Zm9ybSBzZW5zb3JzIgo+PiArICAgIGRlcGVuZHMgb24gUFBDX1BP V0VSTlYKPj4gKyAgICBkZWZhdWx0IHkKPj4gKyAgICBoZWxwCj4+ICsgICAgICBJZiB5b3Ugc2F5 IHllcyBoZXJlIHlvdSBnZXQgc3VwcG9ydCBmb3IgdGhlIHRlbXBlcmF0dXJlL2Zhbi9wb3dlcgo+ PiArICAgICAgc2Vuc29ycyBvbiB5b3VyIHBsYXRmb3JtLgo+PiArCj4+ICAgY29uZmlnIFNFTlNP UlNfSUlPX0hXTU9OCj4+ICAgICAgIHRyaXN0YXRlICJId21vbiBkcml2ZXIgdGhhdCB1c2VzIGNo YW5uZWxzIHNwZWNpZmllZCB2aWEgaWlvIG1hcHMiCj4+ICAgICAgIGRlcGVuZHMgb24gSUlPCj4+ IGRpZmYgLS1naXQgYS9kcml2ZXJzL2h3bW9uL01ha2VmaWxlIGIvZHJpdmVycy9od21vbi9NYWtl ZmlsZQo+PiBpbmRleCBjNDhmOTg3Li4xOTljNDAxIDEwMDY0NAo+PiAtLS0gYS9kcml2ZXJzL2h3 bW9uL01ha2VmaWxlCj4+ICsrKyBiL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUKPj4gQEAgLTcxLDYg KzcxLDcgQEAgb2JqLSQoQ09ORklHX1NFTlNPUlNfVUxUUkE0NSkgICAgKz0gdWx0cmE0NV9lbnYu bwo+PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0k1S19BTUIpICAgICs9IGk1a19hbWIubwo+PiAg IG9iai0kKENPTkZJR19TRU5TT1JTX0lCTUFFTSkgICAgKz0gaWJtYWVtLm8KPj4gICBvYmotJChD T05GSUdfU0VOU09SU19JQk1QRVgpICAgICs9IGlibXBleC5vCj4+ICtvYmotJChDT05GSUdfU0VO U09SU19JQk1QT1dFUk5WKSs9IGlibXBvd2VybnYubwo+PiAgIG9iai0kKENPTkZJR19TRU5TT1JT X0lJT19IV01PTikgKz0gaWlvX2h3bW9uLm8KPj4gICBvYmotJChDT05GSUdfU0VOU09SU19JTkEy MDkpICAgICs9IGluYTIwOS5vCj4+ICAgb2JqLSQoQ09ORklHX1NFTlNPUlNfSU5BMlhYKSAgICAr PSBpbmEyeHgubwo+PiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9od21vbi9pYm1wb3dlcm52LmMgYi9k cml2ZXJzL2h3bW9uL2libXBvd2VybnYuYwo+PiBuZXcgZmlsZSBtb2RlIDEwMDY0NAo+PiBpbmRl eCAwMDAwMDAwLi5hZmNlNjIwCj4+IC0tLSAvZGV2L251bGwKPj4gKysrIGIvZHJpdmVycy9od21v bi9pYm1wb3dlcm52LmMKPj4gQEAgLTAsMCArMSwzNjggQEAKPj4gKy8qCj4+ICsgKiBJQk0gUG93 ZXJOViBwbGF0Zm9ybSBzZW5zb3JzIGZvciB0ZW1wZXJhdHVyZS9mYW4vcG93ZXIKPj4gKyAqIENv cHlyaWdodCAoQykgMjAxNCBJQk0KPj4gKyAqCj4+ICsgKiBUaGlzIHByb2dyYW0gaXMgZnJlZSBz b2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yIG1vZGlmeQo+PiArICogaXQg dW5kZXIgdGhlIHRlcm1zIG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcyBwdWJs aXNoZWQgYnkKPj4gKyAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJz aW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCj4+ICsgKiAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRl ciB2ZXJzaW9uLgo+PiArICoKPj4gKyAqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0 aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAo+PiArICogYnV0IFdJVEhPVVQgQU5ZIFdB UlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YKPj4gKyAqIE1FUkNI QU5UQUJJTElUWSBvciBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRS4gIFNlZSB0aGUK Pj4gKyAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCj4+ICsg Kgo+PiArICogWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVy YWwgUHVibGljIExpY2Vuc2UKPj4gKyAqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLgo+PiArICov Cj4+ICsKPj4gKyNpbmNsdWRlIDxsaW51eC9pbml0Lmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvbW9k dWxlLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgva2VybmVsLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgv aHdtb24uaD4KPj4gKyNpbmNsdWRlIDxsaW51eC9od21vbi1zeXNmcy5oPgo+PiArI2luY2x1ZGUg PGxpbnV4L29mLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvc2xhYi5oPgo+PiArCj4+ICsjaW5jbHVk ZSA8bGludXgvcGxhdGZvcm1fZGV2aWNlLmg+Cj4+ICsjaW5jbHVkZSA8YXNtL29wYWwuaD4KPj4g KyNpbmNsdWRlIDxsaW51eC9lcnIuaD4KPj4gKwo+PiArI2RlZmluZSBEUlZOQU1FICAgICAgICAi aWJtcG93ZXJudiIKPj4gKyNkZWZpbmUgTUFYX0FUVFJfTEVOICAgIDMyCj4+ICsKPj4gKy8qIFNl bnNvciBzdWZmaXggbmFtZSBmcm9tIERUICovCj4+ICsjZGVmaW5lIERUX0ZBVUxUX0FUVFJfU1VG RklYICAgICAgICAiZmF1bHRlZCIKPj4gKyNkZWZpbmUgRFRfREFUQV9BVFRSX1NVRkZJWCAgICAg ICAgImRhdGEiCj4+ICsjZGVmaW5lIERUX1RIUkVTSE9MRF9BVFRSX1NVRkZJWCAgICAidGhycyIK Pj4gKwo+PiArLyoKPj4gKyAqIEVudW1lcmF0ZXMgYWxsIHRoZSB0eXBlcyBvZiBzZW5zb3JzIGlu IHRoZSBQT1dFUk5WIHBsYXRmb3JtIGFuZCAKPj4gZG9lcyBpbmRleAo+PiArICogaW50byAnc3Ry dWN0IHNlbnNvcl9ncm91cCcKPj4gKyAqLwo+PiArZW51bSBzZW5zb3JzIHsKPj4gKyAgICBGQU4s Cj4+ICsgICAgQU1CSUVOVF9URU1QLAo+PiArICAgIFBPV0VSX1NVUFBMWSwKPj4gKyAgICBQT1dF Ul9JTlBVVCwKPj4gKyAgICBNQVhfU0VOU09SX1RZUEUsCj4+ICt9Owo+PiArCj4+ICtzdGF0aWMg c3RydWN0IHNlbnNvcl9ncm91cCB7Cj4+ICsgICAgY29uc3QgY2hhciAqbmFtZTsKPj4gKyAgICBj b25zdCBjaGFyICpjb21wYXRpYmxlOwo+PiArICAgIHN0cnVjdCBhdHRyaWJ1dGVfZ3JvdXAgZ3Jv dXA7Cj4+ICsgICAgdTMyIGF0dHJfY291bnQ7Cj4+ICt9IHNlbnNvcl9ncm91cHNbXSA9IHsKPj4g KyAgICB7ImZhbiIsICJpYm0sb3BhbC1zZW5zb3ItY29vbGluZy1mYW4iLCB7MH0sIDB9LAo+PiAr ICAgIHsidGVtcCIsICJpYm0sb3BhbC1zZW5zb3ItYW1iLXRlbXAiLCB7MH0sIDB9LAo+PiArICAg IHsiaW4iLCAiaWJtLG9wYWwtc2Vuc29yLXBvd2VyLXN1cHBseSIsIHswfSwgMH0sCj4+ICsgICAg eyJwb3dlciIsICJpYm0sb3BhbC1zZW5zb3ItcG93ZXIiLCB7MH0sIDB9Cj4+ICt9Owo+PiArCj4g VGhlICcwJyBpbml0aWFsaXphdGlvbnMgc2hvdWxkIG5vdCBiZSBuZWNlc3NhcnkuCj4KPgo+PiAr c3RydWN0IHNlbnNvcl9kYXRhIHsKPj4gKyAgICB1MzIgaWQ7IC8qIEFuIG9wYXF1ZSBpZCBvZiB0 aGUgZmlybXdhcmUgZm9yIGVhY2ggc2Vuc29yICovCj4+ICsgICAgZW51bSBzZW5zb3JzIHR5cGU7 Cj4+ICsgICAgY2hhciBuYW1lW01BWF9BVFRSX0xFTl07Cj4+ICsgICAgc3RydWN0IGRldmljZV9h dHRyaWJ1dGUgZGV2X2F0dHI7Cj4+ICt9Owo+PiArCj4+ICtzdHJ1Y3QgcGxhdGZvcm1fZGF0YSB7 Cj4+ICsgICAgY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqYXR0cl9ncm91cHNbTUFYX1NF TlNPUl9UWVBFICsgMV07Cj4+ICsgICAgdTMyIHNlbnNvcnNfY291bnQ7IC8qIFRvdGFsIGNvdW50 IG9mIHNlbnNvcnMgZnJvbSBlYWNoIGdyb3VwICovCj4+ICt9Owo+PiArCj4+ICsvKiBQbGF0Zm9y bSBkZXZpY2UgcmVwcmVzZW50aW5nIGFsbCB0aGUgaWJtcG93ZXJudiBzZW5zb3JzICovCj4+ICtz dGF0aWMgc3RydWN0IHBsYXRmb3JtX2RldmljZSAqcGRldmljZTsKPj4gKwo+PiArc3RhdGljIHNz aXplX3Qgc2hvd19zZW5zb3Ioc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgCj4+IGRldmljZV9h dHRyaWJ1dGUgKmRldmF0dHIsCj4+ICsgICAgICAgICAgICAgICBjaGFyICpidWYpCj4+ICt7Cj4+ ICsgICAgc3RydWN0IHNlbnNvcl9kYXRhICpzZGF0YSA9IGNvbnRhaW5lcl9vZihkZXZhdHRyLCBz dHJ1Y3QgCj4+IHNlbnNvcl9kYXRhLAo+PiArICAgICAgICAgICAgICAgICAgICAgICAgIGRldl9h dHRyKTsKPj4gKyAgICBzc2l6ZV90IHJldDsKPj4gKyAgICB1MzIgeDsKPj4gKwo+PiArICAgIHJl dCA9IG9wYWxfZ2V0X3NlbnNvcl9kYXRhKHNkYXRhLT5pZCwgJngpOwo+PiArICAgIGlmIChyZXQp IHsKPj4gKyAgICAgICAgcHJfZXJyKCIlczogRmFpbGVkIHRvIGdldCBvcGFsIHNlbnNvciBkYXRh XG4iLCBfX2Z1bmNfXyk7Cj4+ICsgICAgICAgIHJldHVybiByZXQ7Cj4+ICsgICAgfQo+PiArCj4+ ICsgICAgLyogQ29udmVydCB0ZW1wZXJhdHVyZSB0byBtaWxsaS1kZWdyZWVzICovCj4+ICsgICAg aWYgKHNkYXRhLT50eXBlID09IEFNQklFTlRfVEVNUCkKPj4gKyAgICAgICAgeCAqPSAxMDAwOwo+ PiArICAgIC8qIENvbnZlcnQgcG93ZXIgdG8gbWljcm8td2F0dHMgKi8KPj4gKyAgICBlbHNlIGlm IChzZGF0YS0+dHlwZSA9PSBQT1dFUl9JTlBVVCkKPj4gKyAgICAgICAgeCAqPSAxMDAwMDAwOwo+ PiArCj4+ICsgICAgcmV0dXJuIHNwcmludGYoYnVmLCAiJWRcbiIsIHgpOwo+Cj4geCBpcyB1bnNp Z25lZCwgc28gJXUuCgpEb25lLgoKPgo+PiArfQo+PiArCj4+ICtzdGF0aWMgdm9pZCBfX2luaXQg Z2V0X3NlbnNvcl9pbmRleF9hdHRyKGNvbnN0IGNoYXIgKm5hbWUsIHUzMiAKPj4gKmluZGV4LCBj aGFyICphdHRyKQo+PiArewo+PiArICAgIGNoYXIgKmhhc2hfcG9zID0gc3RyY2hyKG5hbWUsICcj Jyk7Cj4+ICsgICAgY2hhciAqZGFzaF9wb3M7Cj4+ICsgICAgdTMyIGNvcHlfbGVuOwo+PiArICAg IGNoYXIgYnVmWzhdOwo+PiArCj4+ICsgICAgbWVtc2V0KGJ1ZiwgMCwgc2l6ZW9mKGJ1ZikpOwo+ PiArICAgICppbmRleCA9IDA7Cj4+ICsgICAgKmF0dHIgPSAnXDAnOwo+PiArCj4+ICsgICAgaWYg KGhhc2hfcG9zKSB7Cj4+ICsgICAgICAgIGRhc2hfcG9zID0gc3RyY2hyKGhhc2hfcG9zLCAnLScp Owo+PiArICAgICAgICBpZiAoZGFzaF9wb3MpIHsKPj4gKyAgICAgICAgICAgIGNvcHlfbGVuID0g ZGFzaF9wb3MgLSBoYXNoX3BvcyAtIDE7Cj4+ICsgICAgICAgICAgICBpZiAoY29weV9sZW4gPCBz aXplb2YoYnVmKSkgewo+PiArICAgICAgICAgICAgICAgIHN0cm5jcHkoYnVmLCBoYXNoX3BvcyAr IDEsIGNvcHlfbGVuKTsKPj4gKyAgICAgICAgICAgICAgICBzc2NhbmYoYnVmLCAiJWQiLCBpbmRl eCk7Cj4KPiBXaGF0IGlmIHNzY2FuZiBmYWlscyA/IE1pZ2h0IGJlIGFuIGludGVyZXN0aW5nIGV4 ZXJjaXNlIHRvIHRyeSBhbmQgY3JlYXRlCj4gbXVsdGlwbGUgc2Vuc29ycyB3aXRoIGluZGV4IDAg KG9yLCBmb3IgdGhhdCBtYXR0ZXIsIHdpdGggdGhlIHNhbWUgCj4gaW5kZXggdmFsdWUpLgo+IERv IHlvdSBoYXZlIGFueSBwcm90ZWN0aW9uIGFnYWluc3QgYmFkIGlucHV0IGRhdGEgPyBHdWVzcyBu b3Q7IGRpZCB5b3UgCj4gdGVzdAo+IHdoYXQgaGFwcGVucyBpZiB5b3UgcGFzcyBiYWQgZGF0YSB0 byB0aGUgZHJpdmVyIChzdWNoIGFzIGR1cGxpY2F0ZSBzZW5zb3IKPiBlbnRyaWVzKSA/CgpXZWxs LCByZXdyaXRpbmcgdGhpcyBmdW5jdGlvbiB0byByZXR1cm4gdGhlIGVycm9yIGNvZGUgaWYgZmFp bHMuCk5leHQgdmVyc2lvbiB3aWxsIGNvdmVyIHRoZXNlIHRlc3QgY2FzZXMgY292ZXJlZC4gVGhh bmtzLgoKPgo+PiArICAgICAgICAgICAgfQo+PiArCj4+ICsgICAgICAgICAgICBzdHJuY3B5KGF0 dHIsIGRhc2hfcG9zICsgMSwgTUFYX0FUVFJfTEVOKTsKPj4gKyAgICAgICAgfQo+PiArICAgIH0K Pj4gK30KPj4gKwo+PiArLyoKPj4gKyAqIFRoaXMgZnVuY3Rpb24gdHJhbnNsYXRlcyB0aGUgRFQg bm9kZSBuYW1lIGludG8gdGhlICdod21vbicgCj4+IGF0dHJpYnV0ZSBuYW1lLgo+PiArICogSUJN UE9XRVJOViBkZXZpY2Ugbm9kZSBhcHBlYXIgbGlrZSBjb29saW5nLWZhbiMyLWRhdGEsIAo+PiBh bWItdGVtcCMxLXRocnMgZXRjLgo+PiArICogd2hpY2ggbmVlZCB0byBiZSBtYXBwZWQgYXMgZmFu Ml9pbnB1dCwgdGVtcDFfbWF4IHJlc3BlY3RpdmVseSBiZWZvcmUKPj4gKyAqIHBvcHVsYXRpbmcg dGhlbSBpbnNpZGUgaHdtb24gZGV2aWNlIGNsYXNzLi4KPj4gKyAqLwo+PiArc3RhdGljIGludCBf X2luaXQgY3JlYXRlX2h3bW9uX2F0dHJfbmFtZShlbnVtIHNlbnNvcnMgdHlwZSwgY29uc3QgCj4+ IGNoYXIgKm5vZGVfbmFtZSwKPj4gKyAgICAgICAgICAgICAgICAgIGNoYXIgKmh3bW9uX2F0dHJf bmFtZSkKPj4gK3sKPj4gKyAgICBjaGFyIGF0dHJfc3VmZml4W01BWF9BVFRSX0xFTl07Cj4+ICsg ICAgY2hhciAqYXR0cl9uYW1lOwo+PiArICAgIHUzMiBpbmRleDsKPj4gKwo+PiArICAgIGdldF9z ZW5zb3JfaW5kZXhfYXR0cihub2RlX25hbWUsICZpbmRleCwgYXR0cl9zdWZmaXgpOwo+PiArICAg IGlmICghaW5kZXggfHwgIXN0cmxlbihhdHRyX3N1ZmZpeCkpIHsKPj4gKyAgICAgICAgcHJfaW5m bygiJXM6IFNlbnNvciBkZXZpY2Ugbm9kZSBuYW1lIGlzIGludmFsaWQsIG5hbWU6ICVzXG4iLAo+ PiArICAgICAgICAgICAgICAgIF9fZnVuY19fLCBub2RlX25hbWUpOwo+PiArICAgICAgICByZXR1 cm4gLUVJTlZBTDsKPj4gKyAgICB9Cj4+ICsKPj4gKyAgICBpZiAoIXN0cmNtcChhdHRyX3N1ZmZp eCwgRFRfRkFVTFRfQVRUUl9TVUZGSVgpKQo+PiArICAgICAgICBhdHRyX25hbWUgPSAiZmF1bHQi Owo+PiArICAgIGVsc2UgaWYoIXN0cmNtcChhdHRyX3N1ZmZpeCwgRFRfREFUQV9BVFRSX1NVRkZJ WCkpCj4+ICsgICAgICAgIGF0dHJfbmFtZSA9ICJpbnB1dCI7Cj4+ICsgICAgZWxzZSBpZiAoIXN0 cmNtcChhdHRyX3N1ZmZpeCwgRFRfVEhSRVNIT0xEX0FUVFJfU1VGRklYKSkgewo+PiArICAgICAg ICBpZiAodHlwZSA9PSBBTUJJRU5UX1RFTVApCj4+ICsgICAgICAgICAgICBhdHRyX25hbWUgPSAi bWF4IjsKPj4gKyAgICAgICAgZWxzZSBpZiAodHlwZSA9PSBGQU4pCj4+ICsgICAgICAgICAgICBh dHRyX25hbWUgPSAibWluIjsKPj4gKyAgICAgICAgZWxzZQo+PiArICAgICAgICAgICAgcmV0dXJu IC1FTk9FTlQ7Cj4+ICsgICAgfSBlbHNlCj4+ICsgICAgICAgIHJldHVybiAtRU5PRU5UOwo+PiAr Cj4+ICsgICAgc25wcmludGYoaHdtb25fYXR0cl9uYW1lLCBNQVhfQVRUUl9MRU4sICIlcyVkXyVz IiwKPj4gKyAgICAgICAgICAgIHNlbnNvcl9ncm91cHNbdHlwZV0ubmFtZSwgaW5kZXgsIGF0dHJf bmFtZSk7Cj4+ICsgICAgcmV0dXJuIDA7Cj4+ICt9Cj4+ICsKPj4gK3N0YXRpYyBpbnQgX19pbml0 IHBvcHVsYXRlX2F0dHJfZ3JvdXBzKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYpCj4+ICt7 Cj4+ICsgICAgc3RydWN0IHBsYXRmb3JtX2RhdGEgKnBkYXRhID0gcGxhdGZvcm1fZ2V0X2RydmRh dGEocGRldik7Cj4+ICsgICAgY29uc3Qgc3RydWN0IGF0dHJpYnV0ZV9ncm91cCAqKnBncm91cHMg PSBwZGF0YS0+YXR0cl9ncm91cHM7Cj4+ICsgICAgc3RydWN0IGRldmljZV9ub2RlICpvcGFsLCAq bnA7Cj4+ICsgICAgZW51bSBzZW5zb3JzIHR5cGU7Cj4+ICsgICAgaW50IGVyciA9IDA7Cj4+ICsK Pj4gKyAgICBvcGFsID0gb2ZfZmluZF9ub2RlX2J5X3BhdGgoIi9pYm0sb3BhbC9zZW5zb3JzIik7 Cj4+ICsgICAgICAgIGlmICghb3BhbCkgewo+Cj4gQW4gb2J2aW91cyB3aGl0ZXNwYWNlIGVycm9y IGhlcmUuCj4KPj4gKyAgICAgICAgcHJfZXJyKCIlczogT3BhbCAnc2Vuc29ycycgbm9kZSBub3Qg Zm91bmRcbiIsIF9fZnVuY19fKTsKPj4gKyAgICAgICAgcmV0dXJuIC1FTk9ERVY7Cj4+ICsgICAg ICAgIH0KPj4gKwo+PiArICAgIGZvcl9lYWNoX2NoaWxkX29mX25vZGUob3BhbCwgbnApIHsKPj4g KyAgICAgICAgaWYgKG5wLT5uYW1lID09IE5VTEwpCj4+ICsgICAgICAgICAgICBjb250aW51ZTsK Pj4gKwo+PiArICAgICAgICBmb3IgKHR5cGUgPSAwOyB0eXBlIDwgTUFYX1NFTlNPUl9UWVBFOyB0 eXBlKyspCj4+ICsgICAgICAgICAgICBpZiAob2ZfZGV2aWNlX2lzX2NvbXBhdGlibGUobnAsCj4+ ICsgICAgICAgICAgICAgICAgc2Vuc29yX2dyb3Vwc1t0eXBlXS5jb21wYXRpYmxlKSkgewo+PiAr ICAgICAgICAgICAgICAgIHNlbnNvcl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCsrOwo+PiArICAg ICAgICAgICAgICAgIGJyZWFrOwo+PiArICAgICAgICAgICAgfQo+PiArICAgIH0KPgo+IFlvdSBz aG91bGQgYmUgYWJsZSB0byBkbwo+ICAgICBvZl9ub2RlX3B1dChvcGFsKTsKPgo+IGhlcmUuIFRo ZW4geW91IGNhbiByZXR1cm4gaW1tZWRpYXRlbHkgb24gZXJyb3IgYmVsb3cuCgpEb25lLgoKPgo+ PiArCj4+ICsgICAgZm9yICh0eXBlID0gMDsgdHlwZSA8IE1BWF9TRU5TT1JfVFlQRTsgdHlwZSsr KSB7Cj4+ICsgICAgICAgIGlmICghc2Vuc29yX2dyb3Vwc1t0eXBlXS5hdHRyX2NvdW50KQo+PiAr ICAgICAgICAgICAgY29udGludWU7Cj4+ICsKPj4gKyAgICAgICAgc2Vuc29yX2dyb3Vwc1t0eXBl XS5ncm91cC5hdHRycyA9IGRldm1fa3phbGxvYygmcGRldi0+ZGV2LAo+PiArICAgICAgICAgICAg ICAgICAgICBzaXplb2Yoc3RydWN0IGF0dHJpYnV0ZSopICoKPj4gKyAgICAgICAgICAgICAgICAg ICAgKHNlbnNvcl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCArIDEpLAo+PiArICAgICAgICAgICAg ICAgICAgICBHRlBfS0VSTkVMKTsKPj4gKyAgICAgICAgaWYgKCFzZW5zb3JfZ3JvdXBzW3R5cGVd Lmdyb3VwLmF0dHJzKSB7Cj4+ICsgICAgICAgICAgICBwcl9lcnIoIiVzOiBGYWlsZWQgdG8gYWxs b2NhdGUgbWVtb3J5IGZvciBhdHRyaWJ1dGUiCj4+ICsgICAgICAgICAgICAgICAgICAgICJhcnJh eVxuIiwgX19mdW5jX18pOwo+Cj4gZGV2bV9remFsbG9jKCkgYWxyZWFkeSBkdW1wcyBhbiBlcnJv ciBtZXNzYWdlLiBTYW1lIGZvciBhbGwgb3RoZXIgCj4gbWVtb3J5IGVycm9yIG1lc3NhZ2VzLgo+ Cj4+ICsgICAgICAgICAgICBlcnIgPSAtRU5PTUVNOwo+PiArICAgICAgICAgICAgZ290byBleGl0 X3B1dF9ub2RlOwo+PiArICAgICAgICB9Cj4+ICsKPj4gKyAgICAgICAgcGdyb3Vwc1t0eXBlXSA9 ICZzZW5zb3JfZ3JvdXBzW3R5cGVdLmdyb3VwOwo+PiArICAgICAgICBwZGF0YS0+c2Vuc29yc19j b3VudCArPSBzZW5zb3JfZ3JvdXBzW3R5cGVdLmF0dHJfY291bnQ7Cj4+ICsgICAgICAgIHNlbnNv cl9ncm91cHNbdHlwZV0uYXR0cl9jb3VudCA9IDA7Cj4+ICsgICAgfQo+PiArCj4+ICtleGl0X3B1 dF9ub2RlOgo+PiArICAgIG9mX25vZGVfcHV0KG9wYWwpOwo+PiArICAgIHJldHVybiBlcnI7Cj4+ ICt9Cj4+ICsKPj4gKy8qCj4+ICsgKiBJdGVyYXRlIHRocm91Z2ggdGhlIGRldmljZSB0cmVlIGZv ciBlYWNoIGNoaWxkIG9mIHNlbnNvciBub2RlLCAKPj4gY3JlYXRlCj4+ICsgKiBhIHN5c2ZzIGF0 dHJpYnV0ZSBmaWxlLCB0aGUgZmlsZSBpcyBuYW1lZCBieSB0cmFuc2xhdGluZyB0aGUgRFQgCj4+ IG5vZGUgbmFtZQo+PiArICogdG8gdGhlIG5hbWUgcmVxdWlyZWQgYnkgdGhlIGhpZ2hlciAnaHdt b24nIGRyaXZlciBsaWtlIAo+PiBmYW4xX2lucHV0LCB0ZW1wMV9tYXgKPj4gKyAqIGV0Yy4uCj4+ ICsgKi8KPj4gK3N0YXRpYyBpbnQgX19pbml0IGNyZWF0ZV9kZXZpY2VfYXR0cnMoc3RydWN0IHBs YXRmb3JtX2RldmljZSAqcGRldikKPj4gK3sKPj4gKyAgICBzdHJ1Y3QgcGxhdGZvcm1fZGF0YSAq cGRhdGEgPSBwbGF0Zm9ybV9nZXRfZHJ2ZGF0YShwZGV2KTsKPj4gKyAgICBjb25zdCBzdHJ1Y3Qg YXR0cmlidXRlX2dyb3VwICoqcGdyb3VwcyA9IHBkYXRhLT5hdHRyX2dyb3VwczsKPj4gKyAgICBz dHJ1Y3QgZGV2aWNlX25vZGUgKm9wYWwsICpucDsKPj4gKyAgICBzdHJ1Y3Qgc2Vuc29yX2RhdGEg KnNkYXRhOwo+PiArICAgIGNvbnN0IHUzMiAqc2Vuc29yX2lkOwo+PiArICAgIGVudW0gc2Vuc29y cyB0eXBlOwo+PiArICAgIHUzMiBjb3VudCA9IDA7Cj4+ICsgICAgaW50IGVyciA9IDA7Cj4+ICsK Pj4gKyAgICBvcGFsID0gb2ZfZmluZF9ub2RlX2J5X3BhdGgoIi9pYm0sb3BhbC9zZW5zb3JzIik7 Cj4+ICsgICAgICAgIGlmICghb3BhbCkgewo+PiArICAgICAgICBwcl9lcnIoIiVzOiBPcGFsICdz ZW5zb3JzJyBub2RlIG5vdCBmb3VuZFxuIiwgX19mdW5jX18pOwo+PiArICAgICAgICByZXR1cm4g LUVOT0RFVjsKPj4gKyAgICAgICAgfQo+PiArCj4+ICsgICAgc2RhdGEgPSBkZXZtX2t6YWxsb2Mo JnBkZXYtPmRldiwgKHBkYXRhLT5zZW5zb3JzX2NvdW50KSAqCj4+ICsgICAgICAgICAgICAgICAg IHNpemVvZigqc2RhdGEpLCBHRlBfS0VSTkVMKTsKPj4gKyAgICBpZiAoIXNkYXRhKSB7Cj4+ICsg ICAgICAgIHByX2VycigiJXM6IEZhaWxlZCB0byBhbGxvY2F0ZSBtZW1vcnkgZm9yIHRoZSBzZW5z b3JfZGF0YSIsCj4+ICsgICAgICAgICAgICAgICAgX19mdW5jX18pOwo+PiArICAgICAgICBlcnIg PSAtRU5PTUVNOwo+PiArICAgICAgICBnb3RvIGV4aXRfcHV0X25vZGU7Cj4+ICsgICAgfQo+PiAr Cj4+ICsgICAgZm9yX2VhY2hfY2hpbGRfb2Zfbm9kZShvcGFsLCBucCkgewo+PiArICAgICAgICAg ICAgICAgIGlmIChucC0+bmFtZSA9PSBOVUxMKQo+PiArICAgICAgICAgICAgICAgICAgICAgICAg Y29udGludWU7Cj4+ICsKPj4gKyAgICAgICAgZm9yICh0eXBlID0gMDsgdHlwZSA8IE1BWF9TRU5T T1JfVFlQRTsgdHlwZSsrKQo+PiArICAgICAgICAgICAgaWYgKG9mX2RldmljZV9pc19jb21wYXRp YmxlKG5wLAo+PiArICAgICAgICAgICAgICAgICAgICBzZW5zb3JfZ3JvdXBzW3R5cGVdLmNvbXBh dGlibGUpKQo+PiArICAgICAgICAgICAgICAgIGJyZWFrOwo+PiArCj4+ICsgICAgICAgIGlmICh0 eXBlID09IE1BWF9TRU5TT1JfVFlQRSkKPj4gKyAgICAgICAgICAgIGNvbnRpbnVlOwo+PiArCj4+ ICsgICAgICAgIHNlbnNvcl9pZCA9IG9mX2dldF9wcm9wZXJ0eShucCwgInNlbnNvci1pZCIsIE5V TEwpOwo+PiArICAgICAgICBpZiAoIXNlbnNvcl9pZCkgewo+PiArICAgICAgICAgICAgcHJfaW5m bygiJXM6ICVzIGRvZXNuJ3QgaGF2ZSBzZW5zb3ItaWRcbiIsIF9fZnVuY19fLAo+PiArICAgICAg ICAgICAgICAgIG5wLT5uYW1lKTsKPj4gKyAgICAgICAgICAgIGNvbnRpbnVlOwo+PiArICAgICAg ICB9Cj4+ICsKPiBDb25zaWRlciB1c2luZyBvZl9wcm9wZXJ0eV9yZWFkX3UzMigpLgoKT2theS4K Cj4KPj4gKyAgICAgICAgc2RhdGFbY291bnRdLmlkID0gKnNlbnNvcl9pZDsKPj4gKyAgICAgICAg c2RhdGFbY291bnRdLnR5cGUgPSB0eXBlOwo+PiArICAgICAgICBlcnIgPSBjcmVhdGVfaHdtb25f YXR0cl9uYW1lKHR5cGUsIG5wLT5uYW1lLCAKPj4gc2RhdGFbY291bnRdLm5hbWUpOwo+PiArICAg ICAgICBpZiAoZXJyKQo+PiArICAgICAgICAgICAgZ290byBleGl0X3B1dF9ub2RlOwo+PiArCj4+ ICsgICAgICAgIHN5c2ZzX2F0dHJfaW5pdCgmc2RhdGFbY291bnRdLmRldl9hdHRyLmF0dHIpOwo+ PiArICAgICAgICBzZGF0YVtjb3VudF0uZGV2X2F0dHIuYXR0ci5uYW1lID0gc2RhdGFbY291bnRd Lm5hbWU7Cj4+ICsgICAgICAgIHNkYXRhW2NvdW50XS5kZXZfYXR0ci5hdHRyLm1vZGUgPSBTX0lS VUdPOwo+PiArICAgICAgICBzZGF0YVtjb3VudF0uZGV2X2F0dHIuc2hvdyA9IHNob3dfc2Vuc29y Owo+PiArCj4+ICsgcGdyb3Vwc1t0eXBlXS0+YXR0cnNbc2Vuc29yX2dyb3Vwc1t0eXBlXS5hdHRy X2NvdW50KytdID0KPj4gKyAgICAgICAgICAgICAgICAmc2RhdGFbY291bnQrK10uZGV2X2F0dHIu YXR0cjsKPj4gKyAgICB9Cj4+ICsKPj4gK2V4aXRfcHV0X25vZGU6Cj4+ICsgICAgb2Zfbm9kZV9w dXQob3BhbCk7Cj4+ICsgICAgcmV0dXJuIGVycjsKPj4gK30KPj4gKwo+PiArc3RhdGljIGludCBf X2luaXQgaWJtcG93ZXJudl9wcm9iZShzdHJ1Y3QgcGxhdGZvcm1fZGV2aWNlICpwZGV2KQo+PiAr ewo+PiArICAgIHN0cnVjdCBwbGF0Zm9ybV9kYXRhICpwZGF0YTsKPj4gKyAgICBzdHJ1Y3QgZGV2 aWNlICpod21vbl9kZXY7Cj4+ICsgICAgaW50IGVycjsKPj4gKwo+PiArICAgIHBkYXRhID0gZGV2 bV9remFsbG9jKCZwZGV2LT5kZXYsIHNpemVvZigqcGRhdGEpLCBHRlBfS0VSTkVMKTsKPj4gKyAg ICBpZiAoIXBkYXRhKQo+PiArICAgICAgICByZXR1cm4gLUVOT01FTTsKPj4gKwo+PiArICAgIHBs YXRmb3JtX3NldF9kcnZkYXRhKHBkZXYsIHBkYXRhKTsKPj4gKyAgICBwZGF0YS0+c2Vuc29yc19j b3VudCA9IDA7Cj4+ICsgICAgZXJyID0gcG9wdWxhdGVfYXR0cl9ncm91cHMocGRldik7Cj4+ICsg ICAgaWYgKGVycikKPj4gKyAgICAgICAgcmV0dXJuIGVycjsKPj4gKwo+PiArICAgIC8qIENyZWF0 ZSBzeXNmcyBhdHRyaWJ1dGUgZmlsZSBmb3IgZWFjaCBzZW5zb3IgZm91bmQgaW4gdGhlIERUICov Cj4KPiBBdHRyaWJ1dGUgZGF0YSwgbm90IGZpbGUKPgo+PiArICAgIGVyciA9IGNyZWF0ZV9kZXZp Y2VfYXR0cnMocGRldik7Cj4+ICsgICAgaWYgKGVycikKPj4gKyAgICAgICAgcmV0dXJuIGVycjsK Pj4gKwo+PiArICAgIC8qIEZpbmFsbHksIHJlZ2lzdGVyIHdpdGggaHdtb24gKi8KPj4gKyAgICBo d21vbl9kZXYgPSBkZXZtX2h3bW9uX2RldmljZV9yZWdpc3Rlcl93aXRoX2dyb3VwcygmcGRldi0+ ZGV2LCAKPj4gRFJWTkFNRSwKPj4gKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZGF0 YSwKPj4gKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZGF0YS0+YXR0cl9ncm91cHMp Owo+PiArCj4+ICsgICAgcmV0dXJuIFBUUl9FUlJfT1JfWkVSTyhod21vbl9kZXYpOwo+PiArfQo+ PiArCj4+ICtzdGF0aWMgc3RydWN0IHBsYXRmb3JtX2RyaXZlciBpYm1wb3dlcm52X2RyaXZlciA9 IHsKPj4gKyAgICAuZHJpdmVyID0gewo+PiArICAgICAgICAub3duZXIgPSBUSElTX01PRFVMRSwK Pj4gKyAgICAgICAgLm5hbWUgPSBEUlZOQU1FLAo+PiArICAgIH0sCj4+ICt9Owo+PiArCj4+ICtz dGF0aWMgaW50IF9faW5pdCBpYm1wb3dlcm52X2luaXQodm9pZCkKPj4gK3sKPj4gKyAgICBpbnQg ZXJyOwo+PiArCj4+ICsgICAgcGRldmljZSA9IHBsYXRmb3JtX2RldmljZV9hbGxvYyhEUlZOQU1F LCAwKTsKPj4gKyAgICBpZiAoIXBkZXZpY2UpIHsKPj4gKyAgICAgICAgcHJfZXJyKCIlczogRGV2 aWNlIGFsbG9jYXRpb24gZmFpbGVkXG4iLCBfX2Z1bmNfXyk7Cj4+ICsgICAgICAgIGVyciA9IC1F Tk9NRU07Cj4+ICsgICAgICAgIGdvdG8gZXhpdDsKPj4gKyAgICB9Cj4+ICsKPj4gKyAgICBlcnIg PSBwbGF0Zm9ybV9kZXZpY2VfYWRkKHBkZXZpY2UpOwo+PiArICAgIGlmIChlcnIpIHsKPj4gKyAg ICAgICAgcHJfZXJyKCIlczogRGV2aWNlIGFkZGl0aW9uIGZhaWxlZCAoJWQpXG4iLCBfX2Z1bmNf XywgZXJyKTsKPj4gKyAgICAgICAgZ290byBleGl0X2RldmljZV9wdXQ7Cj4+ICsgICAgfQo+PiAr Cj4+ICsgICAgZXJyID0gcGxhdGZvcm1fZHJpdmVyX3Byb2JlKCZpYm1wb3dlcm52X2RyaXZlciwg aWJtcG93ZXJudl9wcm9iZSk7Cj4+ICsgICAgaWYgKGVycikgewo+PiArICAgICAgICBwcl9lcnIo IiVzOiBQbGF0ZnJvbSBkcml2ZXIgcHJvYmUgZmFpbGVkXG4iLCBfX2Z1bmNfXyk7Cj4+ICsgICAg ICAgIGdvdG8gZXhpdF9kZXZpY2VfZGVsOwo+PiArICAgIH0KPj4gKwo+PiArICAgIHJldHVybiAw Owo+PiArCj4+ICtleGl0X2RldmljZV9kZWw6Cj4+ICsgICAgcGxhdGZvcm1fZGV2aWNlX2RlbChw ZGV2aWNlKTsKPj4gK2V4aXRfZGV2aWNlX3B1dDoKPj4gKyAgICBwbGF0Zm9ybV9kZXZpY2VfcHV0 KHBkZXZpY2UpOwo+PiArZXhpdDoKPj4gKyAgICByZXR1cm4gZXJyOwo+PiArfQo+PiArCj4+ICtz dGF0aWMgdm9pZCBfX2V4aXQgaWJtcG93ZXJudl9leGl0KHZvaWQpCj4+ICt7Cj4+ICsgICAgcGxh dGZvcm1fZHJpdmVyX3VucmVnaXN0ZXIoJmlibXBvd2VybnZfZHJpdmVyKTsKPj4gKyAgICBwbGF0 Zm9ybV9kZXZpY2VfdW5yZWdpc3RlcihwZGV2aWNlKTsKPj4gK30KPj4gKwo+PiArTU9EVUxFX0FV VEhPUigiTmVlbGVzaCBHdXB0YSA8bmVlbGVndXBAbGludXgudm5ldC5pYm0uY29tPiIpOwo+PiAr TU9EVUxFX0RFU0NSSVBUSU9OKCJJQk0gUE9XRVJOViBwbGF0Zm9ybSBzZW5zb3JzIik7Cj4+ICtN T0RVTEVfTElDRU5TRSgiR1BMIik7Cj4+ICsKPj4gK21vZHVsZV9pbml0KGlibXBvd2VybnZfaW5p dCk7Cj4+ICttb2R1bGVfZXhpdChpYm1wb3dlcm52X2V4aXQpOwo+Pgo+Pgo+Pgo+CgoKX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX18KbG0tc2Vuc29ycyBtYWls aW5nIGxpc3QKbG0tc2Vuc29yc0BsbS1zZW5zb3JzLm9yZwpodHRwOi8vbGlzdHMubG0tc2Vuc29y cy5vcmcvbWFpbG1hbi9saXN0aW5mby9sbS1zZW5zb3Jz ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-05-28 7:23 ` Guenter Roeck @ 2014-06-18 8:55 ` Neelesh Gupta -1 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-06-18 8:43 UTC (permalink / raw) To: Guenter Roeck, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat >> +} >> + >> +static void __init get_sensor_index_attr(const char *name, u32 >> *index, char *attr) >> +{ >> + char *hash_pos = strchr(name, '#'); >> + char *dash_pos; >> + u32 copy_len; >> + char buf[8]; >> + >> + memset(buf, 0, sizeof(buf)); >> + *index = 0; >> + *attr = '\0'; >> + >> + if (hash_pos) { >> + dash_pos = strchr(hash_pos, '-'); >> + if (dash_pos) { >> + copy_len = dash_pos - hash_pos - 1; >> + if (copy_len < sizeof(buf)) { >> + strncpy(buf, hash_pos + 1, copy_len); >> + sscanf(buf, "%d", index); > > What if sscanf fails ? Might be an interesting exercise to try and create > multiple sensors with index 0 (or, for that matter, with the same > index value). > Do you have any protection against bad input data ? Guess not; did you > test > what happens if you pass bad data to the driver (such as duplicate sensor > entries) ? We can't have duplicate entries in the device tree under the same node ? But yes, rest other scenarios must be validated. - Neelesh > >> + } >> + >> + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); >> + } >> + } >> +} >> + >> + >> > > _______________________________________________ > Linuxppc-dev mailing list > Linuxppc-dev@lists.ozlabs.org > https://lists.ozlabs.org/listinfo/linuxppc-dev ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-06-18 8:55 ` Neelesh Gupta 0 siblings, 0 replies; 18+ messages in thread From: Neelesh Gupta @ 2014-06-18 8:55 UTC (permalink / raw) To: Guenter Roeck, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat >> +} >> + >> +static void __init get_sensor_index_attr(const char *name, u32 >> *index, char *attr) >> +{ >> + char *hash_pos = strchr(name, '#'); >> + char *dash_pos; >> + u32 copy_len; >> + char buf[8]; >> + >> + memset(buf, 0, sizeof(buf)); >> + *index = 0; >> + *attr = '\0'; >> + >> + if (hash_pos) { >> + dash_pos = strchr(hash_pos, '-'); >> + if (dash_pos) { >> + copy_len = dash_pos - hash_pos - 1; >> + if (copy_len < sizeof(buf)) { >> + strncpy(buf, hash_pos + 1, copy_len); >> + sscanf(buf, "%d", index); > > What if sscanf fails ? Might be an interesting exercise to try and create > multiple sensors with index 0 (or, for that matter, with the same > index value). > Do you have any protection against bad input data ? Guess not; did you > test > what happens if you pass bad data to the driver (such as duplicate sensor > entries) ? We can't have duplicate entries in the device tree under the same node ? But yes, rest other scenarios must be validated. - Neelesh > >> + } >> + >> + strncpy(attr, dash_pos + 1, MAX_ATTR_LEN); >> + } >> + } >> +} >> + >> + >> > > _______________________________________________ > Linuxppc-dev mailing list > Linuxppc-dev@lists.ozlabs.org > https://lists.ozlabs.org/listinfo/linuxppc-dev _______________________________________________ lm-sensors mailing list lm-sensors@lm-sensors.org http://lists.lm-sensors.org/mailman/listinfo/lm-sensors ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [lm-sensors] [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature 2014-06-18 8:55 ` [lm-sensors] " Neelesh Gupta @ 2014-06-18 13:05 ` Guenter Roeck -1 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-06-18 13:05 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 06/18/2014 01:43 AM, Neelesh Gupta wrote: > >>> +} >>> + >>> +static void __init get_sensor_index_attr(const char *name, u32 *index, char *attr) >>> +{ >>> + char *hash_pos = strchr(name, '#'); >>> + char *dash_pos; >>> + u32 copy_len; >>> + char buf[8]; >>> + >>> + memset(buf, 0, sizeof(buf)); >>> + *index = 0; >>> + *attr = '\0'; >>> + >>> + if (hash_pos) { >>> + dash_pos = strchr(hash_pos, '-'); >>> + if (dash_pos) { >>> + copy_len = dash_pos - hash_pos - 1; >>> + if (copy_len < sizeof(buf)) { >>> + strncpy(buf, hash_pos + 1, copy_len); >>> + sscanf(buf, "%d", index); >> >> What if sscanf fails ? Might be an interesting exercise to try and create >> multiple sensors with index 0 (or, for that matter, with the same index value). >> Do you have any protection against bad input data ? Guess not; did you test >> what happens if you pass bad data to the driver (such as duplicate sensor >> entries) ? > > We can't have duplicate entries in the device tree under the same node ? > But yes, rest other scenarios must be validated. > Was this a serious question ? Sorry, I wonder. It seems quite unlikely for a file system to accept two files with the same name in the same directory. Guenter _______________________________________________ lm-sensors mailing list lm-sensors@lm-sensors.org http://lists.lm-sensors.org/mailman/listinfo/lm-sensors ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature @ 2014-06-18 13:05 ` Guenter Roeck 0 siblings, 0 replies; 18+ messages in thread From: Guenter Roeck @ 2014-06-18 13:05 UTC (permalink / raw) To: Neelesh Gupta, linuxppc-dev, jdelvare, lm-sensors; +Cc: sbhat On 06/18/2014 01:43 AM, Neelesh Gupta wrote: > >>> +} >>> + >>> +static void __init get_sensor_index_attr(const char *name, u32 *index, char *attr) >>> +{ >>> + char *hash_pos = strchr(name, '#'); >>> + char *dash_pos; >>> + u32 copy_len; >>> + char buf[8]; >>> + >>> + memset(buf, 0, sizeof(buf)); >>> + *index = 0; >>> + *attr = '\0'; >>> + >>> + if (hash_pos) { >>> + dash_pos = strchr(hash_pos, '-'); >>> + if (dash_pos) { >>> + copy_len = dash_pos - hash_pos - 1; >>> + if (copy_len < sizeof(buf)) { >>> + strncpy(buf, hash_pos + 1, copy_len); >>> + sscanf(buf, "%d", index); >> >> What if sscanf fails ? Might be an interesting exercise to try and create >> multiple sensors with index 0 (or, for that matter, with the same index value). >> Do you have any protection against bad input data ? Guess not; did you test >> what happens if you pass bad data to the driver (such as duplicate sensor >> entries) ? > > We can't have duplicate entries in the device tree under the same node ? > But yes, rest other scenarios must be validated. > Was this a serious question ? Sorry, I wonder. It seems quite unlikely for a file system to accept two files with the same name in the same directory. Guenter ^ permalink raw reply [flat|nested] 18+ messages in thread
end of thread, other threads:[~2014-06-18 13:05 UTC | newest] Thread overview: 18+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2014-05-19 14:26 [PATCH v2] powerpc/powernv: hwmon driver for power values, fan rpm and temperature Neelesh Gupta 2014-05-19 14:38 ` [lm-sensors] " Neelesh Gupta 2014-05-26 6:22 ` Neelesh Gupta 2014-05-26 6:34 ` [lm-sensors] " Neelesh Gupta 2014-05-26 14:12 ` Guenter Roeck 2014-05-26 14:12 ` Guenter Roeck 2014-05-28 7:23 ` [lm-sensors] " Guenter Roeck 2014-05-28 7:23 ` Guenter Roeck 2014-05-28 7:41 ` [lm-sensors] " Benjamin Herrenschmidt 2014-05-28 7:41 ` Benjamin Herrenschmidt 2014-05-30 14:05 ` Neelesh Gupta 2014-05-30 14:17 ` [lm-sensors] " Neelesh Gupta 2014-06-09 8:15 ` Neelesh Gupta 2014-06-09 8:27 ` [lm-sensors] " Neelesh Gupta 2014-06-18 8:43 ` Neelesh Gupta 2014-06-18 8:55 ` [lm-sensors] " Neelesh Gupta 2014-06-18 13:05 ` Guenter Roeck 2014-06-18 13:05 ` Guenter Roeck
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.