lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Date:   Mon, 19 Mar 2018 15:30:38 +0530
From:   Rajneesh Bhardwaj <rajneesh.bhardwaj@...el.com>
To:     "Rafael J. Wysocki" <rjw@...ysocki.net>
Cc:     Linux ACPI <linux-acpi@...r.kernel.org>,
        Linux PM <linux-pm@...r.kernel.org>,
        LKML <linux-kernel@...r.kernel.org>,
        Mika Westerberg <mika.westerberg@...ux.intel.com>,
        Andy Shevchenko <andriy.shevchenko@...ux.intel.com>
Subject: Re: [PATCH] ACPI: Add Time and Alarm Device (TAD) driver

On Fri, Mar 16, 2018 at 01:51:01PM +0100, Rafael J. Wysocki wrote:
> From: Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> 
> Introduce a driver for the ACPI Time and Alarm Device (TAD) based on
> Section 9.18 of ACPI 6.2.

Does UEFI bios for CNL support it already? Perhaps we can try this out and
share some feedback. Some minor styling related comments below.

> 
> This driver only supports the system wakeup capabilities of the TAD
> which are mandatory.  Support for the RTC capabilities of the TAD

I guess two whitespaces are put intentionally. IMO, even one looks as good
or better.

> will be added to it in the future.
> 
> This driver is entirely sysfs-based.  It provides attributes (under

Ditto

> the TAD platform device) to allow user space to manage the AC and DC
> wakeup timers of the TAD: set and read their values, set and check
> their expire timer wake policies, check and clear their status and
> check the capabilities of the TAD reported by AML.  The DC timer

Ditto, and elsewhere too below.

> attributes are only present if the TAD supports a separate DC alarm
> timer.
> 
> The wakeup events handling and power management of the TAD is
> expected to be taken care of by the ACPI PM domain attached to its
> platform device.
> 
> Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> ---
>  Documentation/ABI/testing/sysfs-devices-platform-ACPI-TAD |  113 +++
>  drivers/acpi/Kconfig                                      |   14 
>  drivers/acpi/Makefile                                     |    1 
>  drivers/acpi/acpi_tad.c                                   |  473 ++++++++++++++
>  4 files changed, 601 insertions(+)

Please update MAINTAINERS too.

> 
> Index: linux-pm/drivers/acpi/Kconfig
> ===================================================================
> --- linux-pm.orig/drivers/acpi/Kconfig
> +++ linux-pm/drivers/acpi/Kconfig
> @@ -217,6 +217,20 @@ config ACPI_FAN
>  	  To compile this driver as a module, choose M here:
>  	  the module will be called fan.
>  
> +config ACPI_TAD
> +	tristate "ACPI Time and Alarm (TAD) Device Support"
> +	depends on SYSFS && PM_SLEEP
> +	default n

This may be removed.

> +	help
> +	  The ACPI Time and Alarm (TAD) device is an alternative to the Real
> +	  Time Clock (RTC).  Its wake timers allow the system to transition from
> +	  the S3 (or optionally S4/S5) state to S0 state after a time period
> +	  elapses.  In comparison with the RTC Alarm, the TAD provides a larger
> +	  scale of flexibility in the wake timers.  The time capabilities of the
> +	  TAD maintain the time of day information across platform power
> +	  transitions, and keep track of time even when the platform is turned
> +	  off.
> +
>  config ACPI_DOCK
>  	bool "Dock"
>  	help
> Index: linux-pm/drivers/acpi/Makefile
> ===================================================================
> --- linux-pm.orig/drivers/acpi/Makefile
> +++ linux-pm/drivers/acpi/Makefile
> @@ -70,6 +70,7 @@ obj-$(CONFIG_ACPI_AC) 		+= ac.o
>  obj-$(CONFIG_ACPI_BUTTON)	+= button.o
>  obj-$(CONFIG_ACPI_FAN)		+= fan.o
>  obj-$(CONFIG_ACPI_VIDEO)	+= video.o
> +obj-$(CONFIG_ACPI_TAD)		+= acpi_tad.o
>  obj-$(CONFIG_ACPI_PCI_SLOT)	+= pci_slot.o
>  obj-$(CONFIG_ACPI_PROCESSOR)	+= processor.o
>  obj-$(CONFIG_ACPI)		+= container.o
> Index: linux-pm/drivers/acpi/acpi_tad.c
> ===================================================================
> --- /dev/null
> +++ linux-pm/drivers/acpi/acpi_tad.c
> @@ -0,0 +1,473 @@
> +// SPDX-License-Identifier: GPL-2.0
> +/*
> + * ACPI Time and Alarm (TAD) Device Driver
> + *
> + * Copyright (C) 2018 Intel Corporation
> + * Author: Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> + *
> + * This driver is based on Section 9.18 of the ACPI 6.2 specification revision.
> + *
> + * It only supports the system wakeup capabilities of the TAD.
> + *
> + * Provided are sysfs attributes, available under the TAD platform device,
> + * allowing user space to manage the AC and DC wakeup timers of the TAD:
> + * set and read their values, set and check their expire timer wake policies,
> + * check and clear their status and check the capabilities of the TAD reported
> + * by AML.  The DC timer attributes are only present if the TAD supports a
> + * separate DC alarm timer.
> + *
> + * The wakeup events handling and power management of the TAD is expected to
> + * be taken care of by the ACPI PM domain attached to its platform device.
> + */
> +
> +#include <linux/acpi.h>
> +#include <linux/kernel.h>
> +#include <linux/module.h>
> +#include <linux/platform_device.h>
> +#include <linux/pm_runtime.h>
> +#include <linux/suspend.h>
> +
> +MODULE_LICENSE("GPL v2");
> +MODULE_AUTHOR("Rafael J. Wysocki");
> +
> +/* ACPI TAD capability flags (ACPI 6.2, Section 9.18.2) */
> +#define ACPI_TAD_AC_WAKE	BIT(0)
> +#define ACPI_TAD_DC_WAKE	BIT(1)
> +#define ACPI_TAD_RT		BIT(2)
> +#define ACPI_TAD_RT_IN_MS	BIT(3)
> +#define ACPI_TAD_S4_S5__GWS	BIT(4)
> +#define ACPI_TAD_AC_S4_WAKE	BIT(5)
> +#define ACPI_TAD_AC_S5_WAKE	BIT(6)
> +#define ACPI_TAD_DC_S4_WAKE	BIT(7)
> +#define ACPI_TAD_DC_S5_WAKE	BIT(8)
> +
> +/* ACPI TAD alarm timer selection */
> +#define ACPI_TAD_AC_TIMER	(u32)0
> +#define ACPI_TAD_DC_TIMER	(u32)1
> +
> +/* Special value for disabled timer or expired timer wake policy. */
> +#define ACPI_TAD_WAKE_DISABLED	(~(u32)0)
> +
> +struct acpi_tad_driver_data {
> +	u32 capabilities;
> +};
> +
> +static int acpi_tad_wake_set(struct device *dev, char *method, u32 timer_id,
> +			     u32 value)
> +{
> +	acpi_handle handle = ACPI_HANDLE(dev);
> +	union acpi_object args[] = {
> +		{ .type = ACPI_TYPE_INTEGER, },
> +		{ .type = ACPI_TYPE_INTEGER, },
> +	};
> +	struct acpi_object_list arg_list = {
> +		.pointer = args,
> +		.count = ARRAY_SIZE(args),
> +	};
> +	unsigned long long retval;
> +	acpi_status status;

though its a matter of personal preference but these can be moved up and a
newline after struct closing brace.

> +
> +	args[0].integer.value = timer_id;
> +	args[1].integer.value = value;
> +
> +	pm_runtime_get_sync(dev);
> +
> +	status = acpi_evaluate_integer(handle, method, &arg_list, &retval);
> +
> +	pm_runtime_put_sync(dev);
> +
> +	if (ACPI_FAILURE(status) || retval)
> +		return -EIO;
> +
> +	return 0;
> +}
> +
> +static int acpi_tad_wake_write(struct device *dev, const char *buf, char *method,

Going abovbe 80.

> +			       u32 timer_id, const char *specval)
> +{
> +	u32 value;
> +
> +	if (sysfs_streq(buf, specval)) {
> +		value = ACPI_TAD_WAKE_DISABLED;
> +	} else {
> +		int ret = kstrtou32(buf, 0, &value);
> +
> +		if (ret)
> +			return ret;
> +
> +		if (value == ACPI_TAD_WAKE_DISABLED)
> +			return -EINVAL;
> +	}
> +
> +	return acpi_tad_wake_set(dev, method, timer_id, value);
> +}
> +
> +static ssize_t acpi_tad_wake_read(struct device *dev, char *buf, char *method,
> +				  u32 timer_id, const char *specval)
> +{
> +	acpi_handle handle = ACPI_HANDLE(dev);
> +	union acpi_object args[] = {
> +		{ .type = ACPI_TYPE_INTEGER, },
> +	};
> +	struct acpi_object_list arg_list = {
> +		.pointer = args,
> +		.count = ARRAY_SIZE(args),
> +	};
> +	unsigned long long retval;
> +	acpi_status status;
> +
> +	args[0].integer.value = timer_id;
> +
> +	pm_runtime_get_sync(dev);
> +
> +	status = acpi_evaluate_integer(handle, method, &arg_list, &retval);
> +
> +	pm_runtime_put_sync(dev);
> +
> +	if (ACPI_FAILURE(status))
> +		return -EIO;
> +
> +	if ((u32)retval == ACPI_TAD_WAKE_DISABLED)
> +		return sprintf(buf, "%s\n", specval);
> +
> +	return sprintf(buf, "%u\n", (u32)retval);
> +}
> +
> +static const char *alarm_specval = "disabled";
> +
> +static int acpi_tad_alarm_write(struct device *dev, const char *buf,
> +				u32 timer_id)
> +{
> +	return acpi_tad_wake_write(dev, buf, "_STV", timer_id, alarm_specval);
> +}
> +
> +static ssize_t acpi_tad_alarm_read(struct device *dev, char *buf, u32 timer_id)
> +{
> +	return acpi_tad_wake_read(dev, buf, "_TIV", timer_id, alarm_specval);
> +}
> +
> +static const char *policy_specval = "never";
> +
> +static int acpi_tad_policy_write(struct device *dev, const char *buf,
> +				 u32 timer_id)
> +{
> +	return acpi_tad_wake_write(dev, buf, "_STP", timer_id, policy_specval);
> +}
> +
> +static ssize_t acpi_tad_policy_read(struct device *dev, char *buf, u32 timer_id)
> +{
> +	return acpi_tad_wake_read(dev, buf, "_TIP", timer_id, policy_specval);
> +}
> +
> +static int acpi_tad_clear_status(struct device *dev, u32 timer_id)
> +{
> +	acpi_handle handle = ACPI_HANDLE(dev);
> +	union acpi_object args[] = {
> +		{ .type = ACPI_TYPE_INTEGER, },
> +	};
> +	struct acpi_object_list arg_list = {
> +		.pointer = args,
> +		.count = ARRAY_SIZE(args),
> +	};
> +	unsigned long long retval;
> +	acpi_status status;
> +
> +	args[0].integer.value = timer_id;
> +
> +	pm_runtime_get_sync(dev);
> +
> +	status = acpi_evaluate_integer(handle, "_CWS", &arg_list, &retval);
> +
> +	pm_runtime_put_sync(dev);
> +
> +	if (ACPI_FAILURE(status) || retval)
> +		return -EIO;
> +
> +	return 0;
> +}
> +
> +static int acpi_tad_status_write(struct device *dev, const char *buf, u32 timer_id)
> +{
> +	int ret, value;
> +
> +	ret = kstrtoint(buf, 0, &value);
> +	if (ret)
> +		return ret;
> +
> +	if (value)
> +		return -EINVAL;
> +
> +	return acpi_tad_clear_status(dev, timer_id);
> +}
> +
> +static ssize_t acpi_tad_status_read(struct device *dev, char *buf, u32 timer_id)
> +{
> +	acpi_handle handle = ACPI_HANDLE(dev);
> +	union acpi_object args[] = {
> +		{ .type = ACPI_TYPE_INTEGER, },
> +	};
> +	struct acpi_object_list arg_list = {
> +		.pointer = args,
> +		.count = ARRAY_SIZE(args),
> +	};
> +	unsigned long long retval;
> +	acpi_status status;
> +
> +	args[0].integer.value = timer_id;
> +
> +	pm_runtime_get_sync(dev);
> +
> +	status = acpi_evaluate_integer(handle, "_GWS", &arg_list, &retval);
> +
> +	pm_runtime_put_sync(dev);
> +
> +	if (ACPI_FAILURE(status))
> +		return -EIO;
> +
> +	return sprintf(buf, "0x%02X\n", (u32)retval);
> +}
> +
> +static ssize_t caps_show(struct device *dev, struct device_attribute *attr,
> +			 char *buf)
> +{
> +	struct acpi_tad_driver_data *dd = dev_get_drvdata(dev);
> +
> +	return sprintf(buf, "0x%02X\n", dd->capabilities);
> +}
> +
> +static DEVICE_ATTR_RO(caps);
> +
> +static ssize_t ac_alarm_store(struct device *dev, struct device_attribute *attr,
> +			      const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_alarm_write(dev, buf, ACPI_TAD_AC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t ac_alarm_show(struct device *dev, struct device_attribute *attr,
> +			     char *buf)
> +{
> +	return acpi_tad_alarm_read(dev, buf, ACPI_TAD_AC_TIMER);
> +}
> +
> +static DEVICE_ATTR(ac_alarm, S_IRUSR | S_IWUSR, ac_alarm_show, ac_alarm_store);
> +
> +static ssize_t ac_policy_store(struct device *dev, struct device_attribute *attr,
> +			       const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_policy_write(dev, buf, ACPI_TAD_AC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t ac_policy_show(struct device *dev, struct device_attribute *attr,
> +			      char *buf)
> +{
> +	return acpi_tad_policy_read(dev, buf, ACPI_TAD_AC_TIMER);
> +}
> +
> +static DEVICE_ATTR(ac_policy, S_IRUSR | S_IWUSR, ac_policy_show, ac_policy_store);
> +
> +static ssize_t ac_status_store(struct device *dev, struct device_attribute *attr,
> +			       const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_status_write(dev, buf, ACPI_TAD_AC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t ac_status_show(struct device *dev, struct device_attribute *attr,
> +			      char *buf)
> +{
> +	return acpi_tad_status_read(dev, buf, ACPI_TAD_AC_TIMER);
> +}
> +
> +static DEVICE_ATTR(ac_status, S_IRUSR | S_IWUSR, ac_status_show, ac_status_store);
> +
> +static struct attribute *acpi_tad_attrs[] = {
> +	&dev_attr_caps.attr,
> +	&dev_attr_ac_alarm.attr,
> +	&dev_attr_ac_policy.attr,
> +	&dev_attr_ac_status.attr,
> +	NULL,
> +};
> +static const struct attribute_group acpi_tad_attr_group = {
> +	.attrs	= acpi_tad_attrs,
> +};
> +
> +static ssize_t dc_alarm_store(struct device *dev, struct device_attribute *attr,
> +			      const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_alarm_write(dev, buf, ACPI_TAD_DC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t dc_alarm_show(struct device *dev, struct device_attribute *attr,
> +			     char *buf)
> +{
> +	return acpi_tad_alarm_read(dev, buf, ACPI_TAD_DC_TIMER);
> +}
> +
> +static DEVICE_ATTR(dc_alarm, S_IRUSR | S_IWUSR, dc_alarm_show, dc_alarm_store);
> +
> +static ssize_t dc_policy_store(struct device *dev, struct device_attribute *attr,
> +			       const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_policy_write(dev, buf, ACPI_TAD_DC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t dc_policy_show(struct device *dev, struct device_attribute *attr,
> +			      char *buf)
> +{
> +	return acpi_tad_policy_read(dev, buf, ACPI_TAD_DC_TIMER);
> +}
> +
> +static DEVICE_ATTR(dc_policy, S_IRUSR | S_IWUSR, dc_policy_show, dc_policy_store);
> +
> +static ssize_t dc_status_store(struct device *dev, struct device_attribute *attr,
> +			       const char *buf, size_t count)
> +{
> +	int ret = acpi_tad_status_write(dev, buf, ACPI_TAD_DC_TIMER);
> +
> +	return ret ? ret : count;
> +}
> +
> +static ssize_t dc_status_show(struct device *dev, struct device_attribute *attr,
> +			      char *buf)
> +{
> +	return acpi_tad_status_read(dev, buf, ACPI_TAD_DC_TIMER);
> +}
> +
> +static DEVICE_ATTR(dc_status, S_IRUSR | S_IWUSR, dc_status_show, dc_status_store);
> +
> +static struct attribute *acpi_tad_dc_attrs[] = {
> +	&dev_attr_dc_alarm.attr,
> +	&dev_attr_dc_policy.attr,
> +	&dev_attr_dc_status.attr,
> +	NULL,
> +};

Newline.

> +static const struct attribute_group acpi_tad_dc_attr_group = {
> +	.attrs	= acpi_tad_dc_attrs,
> +};
> +
> +static int acpi_tad_disable_timer(struct device *dev, u32 timer_id)
> +{
> +	return acpi_tad_wake_set(dev, "_STV", timer_id, ACPI_TAD_WAKE_DISABLED);
> +}
> +
> +static int acpi_tad_remove(struct platform_device *pdev)
> +{
> +	struct device *dev = &pdev->dev;
> +	struct acpi_tad_driver_data *dd = dev_get_drvdata(dev);
> +
> +	device_init_wakeup(dev, false);
> +
> +	pm_runtime_get_sync(dev);
> +
> +	if (dd->capabilities & ACPI_TAD_DC_WAKE)
> +		sysfs_remove_group(&dev->kobj, &acpi_tad_dc_attr_group);
> +
> +	sysfs_remove_group(&dev->kobj, &acpi_tad_attr_group);
> +
> +	acpi_tad_disable_timer(dev, ACPI_TAD_AC_TIMER);
> +	acpi_tad_clear_status(dev, ACPI_TAD_AC_TIMER);
> +	if (dd->capabilities & ACPI_TAD_DC_WAKE) {
> +		acpi_tad_disable_timer(dev, ACPI_TAD_DC_TIMER);
> +		acpi_tad_clear_status(dev, ACPI_TAD_DC_TIMER);
> +	}
> +
> +	pm_runtime_put_sync(dev);
> +	pm_runtime_disable(dev);
> +	return 0;
> +}
> +
> +static int acpi_tad_probe(struct platform_device *pdev)
> +{
> +	struct device *dev = &pdev->dev;
> +	acpi_handle handle = ACPI_HANDLE(dev);
> +	struct acpi_tad_driver_data *dd;
> +	acpi_status status;
> +	unsigned long long caps;
> +	int ret;
> +
> +	/*
> +	 * Initialization failure messages are mostly about firmware issues, so
> +	 * print them at the "info" level.
> +	 */
> +	status = acpi_evaluate_integer(handle, "_GCP", NULL, &caps);
> +	if (ACPI_FAILURE(status)) {
> +		dev_info(dev, "Unable to get capabilities\n");
> +		return -ENODEV;
> +	}
> +
> +	if (!(caps & ACPI_TAD_AC_WAKE)) {
> +		dev_info(dev, "Unsupported capabilities\n");
> +		return -ENODEV;
> +	}
> +
> +	if (!acpi_has_method(handle, "_PRW")) {
> +		dev_info(dev, "Missing _PRW\n");
> +		return -ENODEV;
> +	}
> +
> +	dd = devm_kzalloc(dev, sizeof(*dd), GFP_KERNEL);
> +	if (!dd)
> +		return -ENOMEM;
> +
> +	dd->capabilities = caps;
> +	dev_set_drvdata(dev, dd);
> +
> +	/*
> +	 * Assume that the ACPI PM domain has been attached to the device and
> +	 * simply enable system wakeup and runtime PM and put the device into
> +	 * runtime suspend.  Everything else should be taken care of by the ACPI
> +	 * PM domain callbacks.
> +	 */
> +	device_init_wakeup(dev, true);
> +	dev_pm_set_driver_flags(dev, DPM_FLAG_SMART_SUSPEND |
> +				     DPM_FLAG_LEAVE_SUSPENDED);
> +	/*
> +	 * The platform bus type layer tells the ACPI PM domain powers up the
> +	 * device, so set the runtime PM status of it to "active".
> +	 */
> +	pm_runtime_set_active(dev);
> +	pm_runtime_enable(dev);
> +	pm_runtime_suspend(dev);
> +
> +	ret = sysfs_create_group(&dev->kobj, &acpi_tad_attr_group);
> +	if (ret)
> +		goto fail;
> +
> +	if (caps & ACPI_TAD_DC_WAKE) {
> +		ret = sysfs_create_group(&dev->kobj, &acpi_tad_dc_attr_group);
> +		if (ret)
> +			goto fail;
> +	}
> +
> +	return 0;
> +
> +fail:
> +	acpi_tad_remove(pdev);
> +	return ret;
> +}
> +
> +static const struct acpi_device_id acpi_tad_ids[] = {
> +	{"ACPI000E", 0},
> +	{}
> +};
> +
> +static struct platform_driver acpi_tad_driver = {
> +	.driver = {
> +		.name = "acpi-tad",
> +		.acpi_match_table = acpi_tad_ids,
> +	},
> +	.probe = acpi_tad_probe,
> +	.remove = acpi_tad_remove,
> +};
> +MODULE_DEVICE_TABLE(acpi, acpi_tad_ids);
> +
> +module_platform_driver(acpi_tad_driver);
> Index: linux-pm/Documentation/ABI/testing/sysfs-devices-platform-ACPI-TAD
> ===================================================================
> --- /dev/null
> +++ linux-pm/Documentation/ABI/testing/sysfs-devices-platform-ACPI-TAD
> @@ -0,0 +1,113 @@
> +		ACPI Time and Alarm (TAD) device attributes.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/caps
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RO) Hexadecimal bitmask of the TAD attributes are reported by
> +		the platform firmware (see ACPI 6.2, section 9.18.2):
> +
> +		BIT(0): AC wakeup implemented if set
> +		BIT(1): DC wakeup implemented if set
> +		BIT(2): Get/set real time features implemented if set
> +		BIT(3): Real time accuracy in milliseconds if set
> +		BIT(4): Correct status reported for wakeups from S4/S5 if set
> +		BIT(5): The AC timer wakes up from S4 if set
> +		BIT(6): The AC timer wakes up from S5 if set
> +		BIT(7): The DC timer wakes up from S4 if set
> +		BIT(8): The DC timer wakes up from S5 if set
> +
> +		The other bits are reserved.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/ac_alarm
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RW) The AC alarm timer value.
> +
> +		Reads return the current AC alarm timer value in seconds or
> +		"disabled", if the AC alarm is not set to wake up the system.
> +
> +		Write a new AC alarm timer value in seconds or "disabled" to it
> +		to set the AC alarm timer or to disable it, respectively.
> +
> +		If the AC alarm timer is set through this attribute and it
> +		expires, it will immediately wake up the system from the S3
> +		sleep state (and from S4/S5 too if supported) until its status
> +		is explicitly cleared via the ac_status attribute.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/ac_policy
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RW) The AC alarm expired timer wake policy (see ACPI 6.2,
> +		Section 9.18 for details).
> +
> +		Reads return the current expired timer wake delay for the AC
> +		alarm timer or "never", if the policy is to discard AC timer
> +		wakeups if the system is on DC power.
> +
> +		Write a new expired timer wake delay for the AC alarm timer in
> +		seconds or "never" to it to set the expired timer wake delay for
> +		the AC alarm timer or to set its expired wake policy to discard
> +		wakeups if the system is on DC power, respectively.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/ac_status
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RW) The AC alarm status.
> +
> +		Reads return a hexadecimal bitmask representing the AC alarm
> +		timer status with the following meaning of bits (see ACPI 6.2,
> +		Section 9.18.5):
> +
> +		Bit(0): The timer has expired if set.
> +		Bit(1): The timer has woken up the system from a sleep state
> +		        (S3 or S4/S5 if supported) if set.
> +
> +		The other bits are reserved.
> +
> +		Reads also cause the AC alarm timer status to be reset.
> +
> +		Another way to reset the the status of the AC alarm timer is to
> +		write (the number) 0 to this file.
> +
> +		If the status return value indicates that the timer has expired,
> +		it will immediately wake up the system from the S3 sleep state
> +		(and from S4/S5 too if supported) until its status is explicitly
> +		cleared through this attribute.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/dc_alarm
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RW,optional) The DC alarm timer value.
> +
> +		This attribute is only present if the TAD supports a separate
> +		DC timer.
> +
> +		It is analogous to the ac_alarm attribute.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/dc_policy
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +Description:
> +		(RW,optional) The DC alarm expired timer wake policy.
> +
> +		This attribute is only present if the TAD supports a separate
> +		DC timer.
> +
> +		It is analogous to the ac_policy attribute.
> +
> +What:		/sys/bus/platform/devices/ACPI000E:00/dc_status
> +Date:		March 2018
> +Contact:	Rafael J. Wysocki <rafael.j.wysocki@...el.com>
> +
> +Description:
> +		(RW,optional) The DC alarm status.
> +
> +		This attribute is only present if the TAD supports a separate
> +		DC timer.
> +
> +		It is analogous to the ac_status attribute.
> 

-- 
Best Regards,
Rajneesh

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ