Commit 242ba665 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull ACPI updates from Rafael Wysocki:
 "From the new functionality perspective, the most significant items
  here are the new driver for the 'ARM Generic Diagnostic Dump and
  Reset' device, the extension of fine grain fan control in the ACPI fan
  driver, and the change making it possible to use CPPC information to
  obtain CPU capacity.

  There are also a few new quirks, a bunch of fixes, including the
  platform-level _OSC handling change to make it actually take the
  platform firmware response into account, some code and documentation
  cleanups, and a notable update of the ACPI device enumeration
  documentation.

  Specifics:

   - Use uintptr_t and offsetof() in the ACPICA code to avoid compiler
     warnings regarding NULL pointer arithmetic (Rafael Wysocki).

   - Fix possible NULL pointer dereference in acpi_ns_walk_namespace()
     when passed "acpi=off" in the command line (Rafael Wysocki).

   - Fix and clean up acpi_os_read/write_port() (Rafael Wysocki).

   - Introduce acpi_bus_for_each_dev() and use it for walking all ACPI
     device objects in the Type C code (Rafael Wysocki).

   - Fix the _OSC platform capabilities negotioation and prevent CPPC
     from being used if the platform firmware indicates that it not
     supported via _OSC (Rafael Wysocki).

   - Use ida_alloc() instead of ida_simple_get() for ACPI enumeration of
     devices (Rafael Wysocki).

   - Add AGDI and CEDT to the list of known ACPI table signatures (Ilkka
     Koskinen, Robert Kiraly).

   - Add power management debug messages related to suspend-to-idle in
     two places (Rafael Wysocki).

   - Fix __acpi_node_get_property_reference() return value and clean up
     that function (Andy Shevchenko, Sakari Ailus).

   - Fix return value of the __setup handler in the ACPI PM timer clock
     source driver (Randy Dunlap).

   - Clean up double words in two comments (Tom Rix).

   - Add "skip i2c clients" quirks for Lenovo Yoga Tablet 1050F/L and
     Nextbook Ares 8 (Hans de Goede).

   - Clean up frequency invariance handling on x86 in the ACPI CPPC
     library (Huang Rui).

   - Work around broken XSDT on the Advantech DAC-BJ01 board (Mark
     Cilissen).

   - Make wakeup events checks in the ACPI EC driver more
     straightforward and clean up acpi_ec_submit_event() (Rafael
     Wysocki).

   - Make it possible to obtain the CPU capacity with the help of CPPC
     information (Ionela Voinescu).

   - Improve fine grained fan control in the ACPI fan driver and
     document it (Srinivas Pandruvada).

   - Add device HID and quirk for Microsoft Surface Go 3 to the ACPI
     battery driver (Maximilian Luz).

   - Make the ACPI driver for Intel SoCs (LPSS) let the SPI driver know
     the exact type of the controller (Andy Shevchenko).

   - Force native backlight mode on Clevo NL5xRU and NL5xNU (Werner
     Sembach).

   - Fix return value of __setup handlers in the APEI code (Randy
     Dunlap).

   - Add Arm Generic Diagnostic Dump and Reset device driver (Ilkka
     Koskinen).

   - Limit printable size of BERT table data (Darren Hart).

   - Fix up HEST and GHES initialization (Shuai Xue).

   - Update the ACPI device enumeration documentation and unify the ASL
     style in GPIO-related examples (Andy Shevchenko)"

* tag 'acpi-5.18-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm: (52 commits)
  clocksource: acpi_pm: fix return value of __setup handler
  ACPI: bus: Avoid using CPPC if not supported by firmware
  Revert "ACPI: Pass the same capabilities to the _OSC regardless of the query flag"
  ACPI: video: Force backlight native for Clevo NL5xRU and NL5xNU
  arm64, topology: enable use of init_cpu_capacity_cppc()
  arch_topology: obtain cpu capacity using information from CPPC
  x86, ACPI: rename init_freq_invariance_cppc() to arch_init_invariance_cppc()
  ACPI: AGDI: Add driver for Arm Generic Diagnostic Dump and Reset device
  ACPI: tables: Add AGDI to the list of known table signatures
  ACPI/APEI: Limit printable size of BERT table data
  ACPI: docs: gpio-properties: Unify ASL style for GPIO examples
  ACPI / x86: Work around broken XSDT on Advantech DAC-BJ01 board
  ACPI: APEI: fix return value of __setup handlers
  x86/ACPI: CPPC: Move init_freq_invariance_cppc() into x86 CPPC
  x86: Expose init_freq_invariance() to topology header
  x86/ACPI: CPPC: Move AMD maximum frequency ratio setting function into x86 CPPC
  x86/ACPI: CPPC: Rename cppc_msr.c to cppc.c
  ACPI / x86: Add skip i2c clients quirk for Lenovo Yoga Tablet 1050F/L
  ACPI / x86: Add skip i2c clients quirk for Nextbook Ares 8
  ACPICA: Avoid walking the ACPI Namespace if it is not there
  ...
parents 346658a5 1bde8bdd
Loading
Loading
Loading
Loading
+28 −0
Original line number Diff line number Diff line
@@ -60,3 +60,31 @@ For example::

When a given field is not populated or its value provided by the platform
firmware is invalid, the "not-defined" string is shown instead of the value.

ACPI Fan Fine Grain Control
=============================

When _FIF object specifies support for fine grain control, then fan speed
can be set from 0 to 100% with the recommended minimum "step size" via
_FSL object. User can adjust fan speed using thermal sysfs cooling device.

Here use can look at fan performance states for a reference speed (speed_rpm)
and set it by changing cooling device cur_state. If the fine grain control
is supported then user can also adjust to some other speeds which are
not defined in the performance states.

The support of fine grain control is presented via sysfs attribute
"fine_grain_control". If fine grain control is present, this attribute
will show "1" otherwise "0".

This sysfs attribute is presented in the same directory as performance states.

ACPI Fan Performance Feedback
=============================

The optional _FST object provides status information for the fan device.
This includes field to provide current fan speed in revolutions per minute
at which the fan is rotating.

This speed is presented in the sysfs using the attribute "fan_speed_rpm",
in the same directory as performance states.
+9 −12
Original line number Diff line number Diff line
@@ -71,14 +71,14 @@ with the help of _DSD (Device Specific Data), introduced in ACPI 5.1::

	Device (FOO) {
		Name (_CRS, ResourceTemplate () {
			GpioIo (Exclusive, ..., IoRestrictionOutputOnly,
				"\\_SB.GPI0") {15} // red
			GpioIo (Exclusive, ..., IoRestrictionOutputOnly,
				"\\_SB.GPI0") {16} // green
			GpioIo (Exclusive, ..., IoRestrictionOutputOnly,
				"\\_SB.GPI0") {17} // blue
			GpioIo (Exclusive, ..., IoRestrictionOutputOnly,
				"\\_SB.GPI0") {1} // power
			GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionOutputOnly,
				"\\_SB.GPI0", 0, ResourceConsumer) { 15 } // red
			GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionOutputOnly,
				"\\_SB.GPI0", 0, ResourceConsumer) { 16 } // green
			GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionOutputOnly,
				"\\_SB.GPI0", 0, ResourceConsumer) { 17 } // blue
			GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionOutputOnly,
				"\\_SB.GPI0", 0, ResourceConsumer) { 1 } // power
		})

		Name (_DSD, Package () {
@@ -92,10 +92,7 @@ with the help of _DSD (Device Specific Data), introduced in ACPI 5.1::
						^FOO, 2, 0, 1,
					}
				},
				Package () {
					"power-gpios",
					Package () {^FOO, 3, 0, 0},
				},
				Package () { "power-gpios", Package () { ^FOO, 3, 0, 0 } },
			}
		})
	}
+44 −67
Original line number Diff line number Diff line
@@ -19,16 +19,17 @@ possible we decided to do following:
    platform devices.

  - Devices behind real busses where there is a connector resource
    are represented as struct spi_device or struct i2c_device
    (standard UARTs are not busses so there is no struct uart_device).
    are represented as struct spi_device or struct i2c_device. Note
    that standard UARTs are not busses so there is no struct uart_device,
    although some of them may be represented by sturct serdev_device.

As both ACPI and Device Tree represent a tree of devices (and their
resources) this implementation follows the Device Tree way as much as
possible.

The ACPI implementation enumerates devices behind busses (platform, SPI and
I2C), creates the physical devices and binds them to their ACPI handle in
the ACPI namespace.
The ACPI implementation enumerates devices behind busses (platform, SPI,
I2C, and in some cases UART), creates the physical devices and binds them
to their ACPI handle in the ACPI namespace.

This means that when ACPI_HANDLE(dev) returns non-NULL the device was
enumerated from ACPI namespace. This handle can be used to extract other
@@ -46,18 +47,16 @@ some minor changes.
Adding ACPI support for an existing driver should be pretty
straightforward. Here is the simplest example::

	#ifdef CONFIG_ACPI
	static const struct acpi_device_id mydrv_acpi_match[] = {
		/* ACPI IDs here */
		{ }
	};
	MODULE_DEVICE_TABLE(acpi, mydrv_acpi_match);
	#endif

	static struct platform_driver my_driver = {
		...
		.driver = {
			.acpi_match_table = ACPI_PTR(mydrv_acpi_match),
			.acpi_match_table = mydrv_acpi_match,
		},
	};

@@ -172,59 +171,51 @@ The SPI device drivers only need to add ACPI IDs in a similar way than with
the platform device drivers. Below is an example where we add ACPI support
to at25 SPI eeprom driver (this is meant for the above ACPI snippet)::

	#ifdef CONFIG_ACPI
	static const struct acpi_device_id at25_acpi_match[] = {
		{ "AT25", 0 },
		{ },
		{ }
	};
	MODULE_DEVICE_TABLE(acpi, at25_acpi_match);
	#endif

	static struct spi_driver at25_driver = {
		.driver = {
			...
			.acpi_match_table = ACPI_PTR(at25_acpi_match),
			.acpi_match_table = at25_acpi_match,
		},
	};

Note that this driver actually needs more information like page size of the
eeprom etc. but at the time writing this there is no standard way of
passing those. One idea is to return this in _DSM method like::
eeprom, etc. This information can be passed via _DSD method like::

	Device (EEP0)
	{
		...
		Method (_DSM, 4, NotSerialized)
		Name (_DSD, Package ()
		{
			Store (Package (6)
			ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
			Package ()
			{
				"byte-len", 1024,
				"addr-mode", 2,
				"page-size, 32
			}, Local0)

			// Check UUIDs etc.

			Return (Local0)
				Package () { "size", 1024 },
				Package () { "pagesize", 32 },
				Package () { "address-width", 16 },
			}
		})
	}

Then the at25 SPI driver can get this configuration by calling _DSM on its
ACPI handle like::

	struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL };
	struct acpi_object_list input;
	acpi_status status;

	/* Fill in the input buffer */
Then the at25 SPI driver can get this configuration by calling device property
APIs during ->probe() phase like::

	status = acpi_evaluate_object(ACPI_HANDLE(&spi->dev), "_DSM",
				      &input, &output);
	if (ACPI_FAILURE(status))
		/* Handle the error */
	err = device_property_read_u32(dev, "size", &size);
	if (err)
		...error handling...

	/* Extract the data here */
	err = device_property_read_u32(dev, "pagesize", &page_size);
	if (err)
		...error handling...

	kfree(output.pointer);
	err = device_property_read_u32(dev, "address-width", &addr_width);
	if (err)
		...error handling...

I2C serial bus support
======================
@@ -237,26 +228,24 @@ registered.
Below is an example of how to add ACPI support to the existing mpu3050
input driver::

	#ifdef CONFIG_ACPI
	static const struct acpi_device_id mpu3050_acpi_match[] = {
		{ "MPU3050", 0 },
		{ },
		{ }
	};
	MODULE_DEVICE_TABLE(acpi, mpu3050_acpi_match);
	#endif

	static struct i2c_driver mpu3050_i2c_driver = {
		.driver	= {
			.name	= "mpu3050",
			.owner	= THIS_MODULE,
			.pm	= &mpu3050_pm,
			.of_match_table = mpu3050_of_match,
			.acpi_match_table = ACPI_PTR(mpu3050_acpi_match),
			.acpi_match_table = mpu3050_acpi_match,
		},
		.probe		= mpu3050_probe,
		.remove		= mpu3050_remove,
		.id_table	= mpu3050_ids,
	};
	module_i2c_driver(mpu3050_i2c_driver);

Reference to PWM device
=======================
@@ -282,9 +271,9 @@ introduced, i.e.::
                    }
                }
            }

        })
        ...
    }

In the above example the PWM-based LED driver references to the PWM channel 0
of \_SB.PCI0.PWM device with initial period setting equal to 600 ms (note that
@@ -306,26 +295,13 @@ For example::
		{
			Name (SBUF, ResourceTemplate()
			{
				...
				// Used to power on/off the device
				GpioIo (Exclusive, PullDefault, 0x0000, 0x0000,
					IoRestrictionOutputOnly, "\\_SB.PCI0.GPI0",
					0x00, ResourceConsumer,,)
				{
					// Pin List
					0x0055
				}
				GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionOutputOnly,
					"\\_SB.PCI0.GPI0", 0, ResourceConsumer) { 85 }

				// Interrupt for the device
				GpioInt (Edge, ActiveHigh, ExclusiveAndWake, PullNone,
					0x0000, "\\_SB.PCI0.GPI0", 0x00, ResourceConsumer,,)
				{
					// Pin list
					0x0058
				}

				...

				GpioInt (Edge, ActiveHigh, ExclusiveAndWake, PullNone, 0,
					 "\\_SB.PCI0.GPI0", 0, ResourceConsumer) { 88 }
			}

			Return (SBUF)
@@ -342,6 +318,7 @@ For example::
			}
		})
		...
	}

These GPIO numbers are controller relative and path "\\_SB.PCI0.GPI0"
specifies the path to the controller. In order to use these GPIOs in Linux
@@ -463,7 +440,7 @@ namespace link::
		Name (_DSD, Package () {
			ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
			Package () {
				Package (2) { "compatible", "ti,tmp75" },
				Package () { "compatible", "ti,tmp75" },
			}
		})
		Method (_CRS, 0, Serialized)
+14 −12
Original line number Diff line number Diff line
@@ -275,6 +275,8 @@ have a device like below::
The driver might expect to get the right GPIO when it does::

  desc = gpiod_get(dev, "reset", GPIOD_OUT_LOW);
  if (IS_ERR(desc))
	...error handling...

but since there is no way to know the mapping between "reset" and
the GpioIo() in _CRS desc will hold ERR_PTR(-ENOENT).
+4 −0
Original line number Diff line number Diff line
@@ -24,6 +24,10 @@ void update_freq_counters_refs(void);
#define arch_scale_freq_capacity topology_get_freq_scale
#define arch_scale_freq_invariant topology_scale_freq_invariant

#ifdef CONFIG_ACPI_CPPC_LIB
#define arch_init_invariance_cppc topology_init_cpu_capacity_cppc
#endif

/* Replace task scheduler's default cpu-invariant accounting */
#define arch_scale_cpu_capacity topology_get_cpu_scale

Loading