I2C enablement with ACPI

Status

  • I2C Controller is enabled on I.MX8MP platform.

  • Supports runtime power management with clock gating.

  • Supports device-specific AML methods to get base clock rate through SCMI interface.

  • Supports pin muxing and configuration for I2C with ACPI pin resources

Changes

AML Code

Device (I2C1) { Name (_HID, "NXP0104") Name (_HRV, 0x1) Name (_UID, 0x1) Name (_CLK, 13) Method (_STA) { Return(0xf) } Name (_PRS, ResourceTemplate () // _PRS: Possible Resource Settings { Interrupt(ResourceConsumer, Level, ActiveHigh, Exclusive) { 67 } }) Method (_CRS, 0x0, NotSerialized) { Name ( RBUF, ResourceTemplate () { MEMORY32FIXED(ReadWrite, 0x30A20000, 0x14, ) Interrupt(ResourceConsumer, Level, ActiveHigh, Exclusive) { 67 } }) Return(RBUF) } Method (_PS0, 0, NotSerialized) // _PS0: Power State 0 { SC07(_CLK, 1) // SCMI method for clock enable } Method (_PS3, 0, NotSerialized) // _PS3: Power State 3 { SC07(_CLK, 0) // SCMI interface for clock gating } Method(GCLK, 0, NotSerialized) { local0 = SC06(_CLK) // SCMI interface to get clock rate Return (local0) } }

I2C Base Clock Rate

I2C controller for the IMX platform needs to know the base clock rate for the controller to configure the clock scaling factors in the controller. For the device tree, this can be specified through clock properties. There are few options available for ACPI

  • Hardcode in the kernel I2C IMX driver

    • There are many devices and drivers following this approach in the Linux kernel. This would work only for fixed clock frequencies.

  • clock-frequency properties in Device specific data (_DSD)

    • clock rate can be specified in ACPI table for the devices under _DSD object. This again works only for fixed clock frequencies

  • Device-specific methods to pass clock rate

    • A specific control method can be added for the devices to get the clock rate. This would work even for variable clock rates. The AML code above uses such a mechanism.

  • ClockInput Resources (Introduced in ACP 6.5)

    • This is not yet implemented in Linux kernel or ACPICA framework.