<html>
    <head>
      <base href="https://bugs.freedesktop.org/" />
    </head>
    <body>
      <p>
        <div>
            <b><a class="bz_bug_link 
          bz_status_NEW "
   title="NEW - [SKL-Y] GuC does not load when resuming from suspend to DISK"
   href="https://bugs.freedesktop.org/show_bug.cgi?id=94390#c5">Comment # 5</a>
              on <a class="bz_bug_link 
          bz_status_NEW "
   title="NEW - [SKL-Y] GuC does not load when resuming from suspend to DISK"
   href="https://bugs.freedesktop.org/show_bug.cgi?id=94390">bug 94390</a>
              from <span class="vcard"><a class="email" href="mailto:david.s.gordon@intel.com" title="david.s.gordon@intel.com">david.s.gordon@intel.com</a>
</span></b>
        <pre>It tuns out that the Linux hibernate/resume cycle is weirdly asymmetric :(

In a suspend (to RAM) cycle, devices are frozen, then the CPU power is turned
"off", leaving the system in a low-power state. On resume, the CPU power comes
up, then devices are thawed and normal operation continues. This is therefore
essentially symmetrical.

In hibernation, OTOH, things are much stranger. First, devices are frozen,
including the display/GPU and presumably the HD/SSD; then, the kernel builds a
compressed hibernation image; then, devices are *thawed* again, and the image
written out. Finally, the power is turned off; there doesn't appear to be any
re-freeze or controlled/phased shutdown at this stage. Therefore, the final
state of devices just before poweroff is "active" -- not a problem for i915 or
the GuC, but potentially an issue for self-powered devices or those with
nonvolatile state.

It's resume-from-hibernation where things really get strange. First, the system
boots as though from cold: BIOS, GRUB, kernel. Drivers are initialised and the
GuC firmware may be loaded. THEN the system discovers the hibernation image. It
doesn't (AFAICT) freeze devices at this point; it simply overwrites the running
kernel with the hibernated image.

This means that the hardware (e.g. GuC) is left active, having been initialised
by the booted kernel. But the reloaded driver state says the device is frozen,
and must be reinitialised, including (re)loading the GuC firmware.

For most devices, reinitialising an already-active device wouldn't be a
problem; but the GuC's program memory is write-once. So when the restored
driver tries to reload the GuC, the write fails.

There are several ways to resolve this; for example, we could ignore the
failure and discover afterwards that the GuC is in fact running anyway. Or we
could check in advance, before even trying to load the GuC, and skip the entire
sequence if it's already loaded. However the preferred solution will be to
reset the GuC just before loading it, this guaranteeing that it starts out in a
known state. (Otherwise, we would at least have to reprogram various options,
and it might still be possible that the state of the running firmware is not
identical with that which the driver would have loaded).

This solution has been coded, tested locally and by the reporter, and sent to
the upstream mailing list.</pre>
        </div>
      </p>
      <hr>
      <span>You are receiving this mail because:</span>
      
      <ul>
          <li>You are on the CC list for the bug.</li>
          <li>You are the QA Contact for the bug.</li>
      </ul>
    </body>
</html>