Re: Tablet mode on L13 Yoga Gen 3

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Just to follow this up, it's not (just?) an acpi issue, the driver
isn't doing what it needs to do - if there is a driver for the
hardware at all.  I'm still looking into what is necessary.

I did write the value to the CMMD variable, but calling the _Q2E
function does not cause the ^HKEY.MHKQ (0x60C0) to be sent.  If I
understand this correctly, that's what should happen.

Thanks,
Liam


On Mon, Jul 22, 2024 at 11:30 PM Liam Howlett <howlett@xxxxxxxxx> wrote:
>
> ..resend in plaintext, apologies if this is the second copy you are reading.
>
> Hello,
>
> I'd like to say first, thanks for the support of thinkpads in linux.
> As a kernel maintainer, I understand this is a lot of work and I
> appreciate you doing a fine job with supporting the hardware.
>
> I am working on patching the thinkpad_acpi driver to support the
> keyboard rotation and keyboard lock-out in tablet mode for the L13
> Yoga Gen 3.  I believe it needs just one bit extra to get working and
> I'm struggling to figure out how to do what I believe is necessary.
>
> It looks like _SB.PCI0.LPC0.EC0.CMMD needs an initial value of 0x01 to
> 0x06, but I don't see a way to trigger this to happen.  Alternatively,
> is there a way to write PMMD?
>
> Right now, I get the following message on boot:
> thinkpad_acpi: Unknown/reserved multi mode value 0x0000 for type 4,
> please report this to ibm-acpi-devel@xxxxxxxxxxxxxxxxxxxxx
>
> It looks like the value of 0 indicates that the keyboard rotate
> monitoring is disabled, but I cannot seem to find an ACPI table way of
> modifying EC0's contents (or set CMMD/PMMD)
>
> The functions of interest seem to be as follows:
>                     Method (_Q2E, 0, NotSerialized)  // _Qxx: EC
> Query, xx=0x00-0xFF
>                     {
>                         Local0 = CMMD /* \_SB_.PCI0.LPC0.EC0_.CMMD */
>                         If (((Local0 != 0x00) && (Local0 <= 0x06)))
>                         {
>                             If ((Local0 != PMMD))
>                             {
>                                 PMMD = Local0
>                                 ^HKEY.MHKQ (0x60C0)
>                                 If ((PMMD >= 0x04))
>                                 {
>                                     WFIO (0x0B, 0x01)
>                                 }
>                                 ElseIf (CPLS)
>                                 {
>                                     WFIO (0x0B, 0x00)
>                                 }
>                                 Else
>                                 {
>                                     WFIO (0x0B, 0x01)
>                                 }
>                             }
>                         }
>
>                         If (((Local0 == 0x00) || (Local0 >= 0x07)))
>                         {
>                             Local1 = 0x01
>                         }
>                         ElseIf (((Local0 == 0x02) || (Local0 ==
> 0x03)))
>                         {
>                             Local1 = 0x02
>                         }
>                         Else
>                         {
>                             Local1 = 0x03
>                         }
>
>                         If ((Local1 != LVMD))
>                         {
>                             LVMD = Local1
>                             Sleep (0x0A)
>                             ^HKEY.MHKQ (0x60F0)
>                         }
>                     }
> ... and ...
>                         Method (GMMS, 1, NotSerialized)
>                         {
>                             Local0 = 0x00040000
>                             Local1 = PMMD /* \PMMD */
>                             If ((Local1 >= 0x06))
>                             {
>                                 Local0 |= 0x03
>                             }
>                             ElseIf ((Local1 >= 0x05))
>                             {
>                                 Local0 |= 0x05
>                             }
>                             ElseIf ((Local1 >= 0x04))
>                             {
>                                 Local0 |= 0x04
>                             }
>                             ElseIf ((Local1 >= 0x03))
>                             {
>                                 Local0 |= 0x02
>                             }
>                             ElseIf ((Local1 >= 0x01))
>                             {
>                                 Local0 |= 0x01
>                             }
>
>                             Return (Local0)
>                         }
> ...
> and this portion of the _WAK code:
>         PMMD = \_SB.PCI0.LPC0.EC0.CMMD
>         If ((PMMD >= 0x07))
>         {
>             PMMD = 0x00
>         }
>
>         LVMD = \_SB.PCI0.LPC0.EC0.CMMD
>         If (((LVMD == 0x00) || (LVMD >= 0x07)))
>         {
>             LVMD = 0x01
>         }
>         ElseIf (((LVMD == 0x02) || (LVMD == 0x03)))
>         {
>             LVMD = 0x02
>         }
>         Else
>         {
>             LVMD = 0x03
>         }
>
> From this, and running acpiexec on the dumped tables, I can see that
> the CMMD value is always 0.  I don't see another function that
> modifies or touches CMMD or PMMD directly, so it seems that this value
> is read but never written by the ACPI itself.  I also see that these
> are the functions that your driver often uses and is trying to
> interact with.  I tried to set the CMMD value in the acpiexec, but it
> won't set RegionField:
> - dump _SB.PCI0.LPC0.EC0.CMMD
> Object 0x55c5a3389490: Namespace Node - Pathname: \_SB.PCI0.LPC0.EC0.CMMD
>     0000: B0 D9 38 A3 C5 55 00 00 0F 11 00 00 43 4D 4D 44  // ..8..U......CMMD
>     0010: E0 3B 38 A3 C5 55 00 00 00 00 00 00 00 00 00 00  // .;8..U..........
>     0020: 00 95 38 A3 C5 55 00 00 01 00 00 00 00 00 00 00  // ..8..U..........
>                 Name : CMMD
>                 Type : 11 [RegionField]
>                Flags : 0000
>             Owner Id : 0001
>          Object List : 0x55c5a338d9b0 RegionField (Type 11)
>               Parent : 0x55c5a3383be0 [EC0_]
>                Child : (nil)
>                 Peer : 0x55c5a3389500 [WFDK]
>
> Attached Object 0x55c5a338d9b0:
>     0000: 00 00 00 00 00 00 00 00 0E 11 01 00 00 01 00 01  // ................
>     0010: 90 94 38 A3 C5 55 00 00 08 00 00 00 C1 00 00 00  // ..8..U..........
>     0020: 00 00 00 00 00 00 00 00 10 3F 38 A3 C5 55 00 00  // .........?8..U..
>     0030: 00 00 00 00 00 00 00 00 80 00 00 00 00 00 00 00  // ................
>     0040: 00 00 00 00 00 00 00 00                          // ........
>                 Type : 11 [RegionField]
>      Reference Count : 0001
>                Flags : 00
>          Object List : (nil) - No attached objects
>          Field Flags : 01
>    Access Byte Width : 01
>           Bit Length : 00000008
>     Field Bit Offset : 00
>     Base Byte Offset : 000000C1
>          Parent Node : 0x55c5a3389490 [CMMD]
>         AccessLength : 00
>        Region Object : 0x55c5a3383f10
>       ResourceBuffer : (nil)
>
> I am nervous about adding a call to write that region field to the
> thinkpad_acpi driver, but there does not appear to be another way to
> modify the entry.  I've searched for CMMD and PMMD in the dsdt.dsl and
> haven't found a way to modify them.
>
> Any help would be appreciated.
>
> Thanks,
> Liam R. Howlett





[Index of Archives]     [Linux Kernel Development]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux