Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Provisioning support in IGPU #586

Closed
vit9696 opened this issue Nov 26, 2019 · 20 comments
Closed

Provisioning support in IGPU #586

vit9696 opened this issue Nov 26, 2019 · 20 comments
Labels

Comments

@vit9696
Copy link
Contributor

vit9696 commented Nov 26, 2019

There are many issues with the matter, and I want to try to raise some attention to the problem from potentially interested parties. I kindly ask people without technical information to ignore this issue.

Problems:

  • Initialting HDCP in the driver leads to IGPU freezes in macOS, and this happens to be done by basically any video.
  • PAVP support is broken, and Intel hardware DRM decoder (used by e.g. Netflix) is not functional.
  • PAVP is not configured to use Apple certificate causing GuC springboard fail to load on SKL+ and resulting in performance issues.

All these issues normally are solved supplemental hacks, as flashing the firmware requires some effort, and ME/HECI is quite a dark forest. Basically, for this to work the following needs to be achived:

  • HDCP/PAVP should be properly initialized by the firmware during boot and potentially during S3.
  • Management Engine firmware should be properly configured.
  • PAVP should use the right key and report «Apple firmware only on Apple HW!» for GuC Springboard to load on SKL+.
  • PAVP should be EPID-provisioned for hardware DRM decoder to work.

What we know:

  • HECI protocol is more or less covered in the official DCMI-HI spec[1], PAVP and EPID are somehow covered in Platform Embedded Security Technology Revealed[2]. There are code samples in EPID SDK[3], some Android firmwares[4], and Intel GPU documents[5]. One can find a little more by searching CMD_SEND_SAFEID_PUBKEY, PAVP_EPID_API_VERSION_MAJOR, PAVP_CMD_HEADER, pavp_lib_session on GitHub code.
  • Apparently Apple uses the same ME firmware as everyone despite our strong suspects that it is not the case. Well, this may still be not true, but we did not find any evidence. Flashing ME firmware 9.5.3.1526 from a Mac on Haswell gives no visible changes.
  • In 12.0.2.1087 ME release pavp application is not encrypted, and apparently this confirms that Apple features are delivered to everyone[6][7][8].
  • SaInitDxe (now AppleMeDriverDxe) in Apple firmware performs EPID provisioning based on epid_provision variable. In the beginning of the year we did some RE on this with @savvamitrofanov. The code works just fine on other platforms, we tested it on four machines (3 haswell, 1 ivy). At this point it can be found in OpenCore vit9696-epid-20191124 branch[9]. Interestingly it also calls some FPF application, which is potentially responsible for permanently locking the configuration, but there is very little information on the matter, it looks similar to coreboot cse code[10], but we did not check much. We also did not try to access FPF on our test machines.
  • The easiest way to test EPID is to play a trailer in QuickTime[11]. Playing a purchased movie will also invoke HDCP, and thus will freeze everything badly. This seems to be because AppleGVA.framework enables HDCP only for high resolutions. WEG will need to be patched to reenable disabled features before testing: Springboard loading[12], PAVP removal[13], forcing software DRM decoder[14].

What we do not know:

  • We basically do not know whether HDCP/PAVP is properly initialised. I would say it is not.
  • We do not know how «Apple firmware only on Apple HW!» is chosen by PAVP. Perhaps it is enough to do EPID provisioning, but we did not try.

Although we are not ready to continue the research at the moment, we believe that it might be helpful to share this information with others. Perhaps somebody wants to continue or has information to share. CC @0xFireWolf, @al3xtjames, @osy86, @platomav, @skochinsky.

[1] https://www.intel.com/content/dam/www/public/us/en/documents/technical-specifications/dcmi-hi-1-0-spec.pdf
[2] https://link.springer.com/content/pdf/10.1007%2F978-1-4302-6572-6.pdf
[3] https://github.com/Intel-EPID-SDK/epid-sdk
[4] https://github.com/shreekantsingh/uefi/tree/master/drivers/misc/mei
[5] https://01.org/sites/default/files/documentation/skl_opregion_rev0p5.pdf
[6] https://twitter.com/platomaniac/status/1031990242545418242
[7] https://github.com/CHEF-KOCH/Intel-ME-Firmware-Repository/tree/master/12
[8] https://github.com/ptresearch/unME12
[9] https://github.com/acidanthera/OcSupportPkg/tree/master/Application/PavpProvision
[10] https://github.com/coreboot/coreboot/blob/master/src/soc/intel/apollolake/cse.c
[11] https://drive.google.com/file/d/12pQ5FFpdHdGOVV6jvbqEq2wmkpMKxsOF/view
[12] https://github.com/acidanthera/WhateverGreen/blob/533611b/WhateverGreen/kern_igfx.cpp#L266-L267
[13] https://github.com/acidanthera/WhateverGreen/blob/533611b/WhateverGreen/kern_igfx.cpp#L270
[14] https://github.com/acidanthera/WhateverGreen/blob/dcbb8d9/WhateverGreen/kern_shiki.cpp#L117

@acidanthera acidanthera deleted a comment from Sniki Dec 3, 2019
@osy
Copy link

osy commented Dec 3, 2019

I'm reading through the resources linked to in the first post. It seems, by construction, what you're proposing is not possible. And if it is, it would be a major security vulnerability for Intel/Apple.

From [2]:

During the setup phase, the EPID authority provides private keys for all platforms, respectively. Note that every platform has a different and unique private key. The delivery and storage of the private key must be protected (encrypted) to avoid leakage. The EPID authority also establishes and manages a server for all verifiers to retrieve EPID group public keys and EPID parameters.

For this EPID ecosystem, Intel acts as the EPID authority. Using the private key, the security and management engine proves that it is a genuine Intel platform, and hence eligible for premium services that are only available for Intel platforms.

On Intel’s security and management engine, the EPID key is treated as an asset of the highest value on the engine. On Intel’s manufacturing line, an EPID key, in its 544-bit compressed and encrypted form, is retrieved from Intel EPID authority’s secure server that generated all keys. The manufacturing process then burns the 544-bit key to secure fuses of the engine. For security and privacy reasons, the key is then immediately and permanently deleted from the secure server. In other words, from that point on, only the part itself knows the value of its EPID private key.

In order to function as a platform, a procedure called “provisioning” must be executed first. The provisioning is a one-time effort for the life of a platform. During provisioning, the group public key and predefined parameters of EPID are sent to the platform from a verifier. The platform uses this data together with its compressed private key to derive the complete private key and then stores the complete private key in secure storage for use in future EPID sessions.

The provisioning must be done before the first invocation of the EPID on a platform. Many platform manufacturers choose to provision in their manufacturing lines for better user experience. Others perform provisioning during system initialization on the first boot. The verifier can be software running on a host operating system or a remote server.

Although the group public key and predefined parameters are not secrets, the platform must verify that what is sent by the verifier is trustworthy. The EPID group pubic key and the predefined parameters are digitally signed by the EPID authority using
ECDSA. The EPID authority’s ECC public key is hardcoded in all platform devices. The platform verifies the EPID authority’s ECDSA signature before using the data sent by the verifiers to perform the private key decompression.

My understanding from this is that for non-Apple devices, Intel acts as the EPID authority, and they issue the EPID private keys (and hold on to the EPID public keys used in the provisioning). For Apple devices, since they're using different certificates, I would assume they are acting as the EPID authority and does the key generation.

That means your non-Apple board is fused with an EPID private keys for which Apple does not hold the public keys to. It also means that you will not be able to provision the group public key because you will not be able to obtain a group public key corresponding to your EPID private key that is ALSO signed by Apple's EPID authority certificate. I am guessing that iTunes DRM content would only be decrypt-able in a chain that eventually ends in an Apple held EPID group public key.

Looking at this from another perspective, if you were a bad guy set on stealing iTunes DRM content and cannot bypass Boot Guard/T2, then why not just buy some random mobo, provision Apple's public keys onto it, and then freely decrypt iTunes DRM? This is precisely what EPID was designed to protect against (enable DRM while also protecting privacy).

Please let me know if I'm misunderstanding this.

@vit9696
Copy link
Contributor Author

vit9696 commented Dec 3, 2019

@osy86 you get the point, but most likely it is not like that. Intel does not let anybody meddle with its rights as an authority, so private keys fused during the manufacturing process are basically random, and should be no different for Apple and non-Apple hardware. Decrypted ME 12 firmware containing Apple specific stuff, group key blobs containing basically all keys, flashed stock chipsets on MacBooks, and ME gladly accepting Apple certificate all that evidence imply that Apple supports all private keys, and it is unimportant whether it is Apple computer or not. As far as I know, recent iTunes versions on Windows do the same thing, just dynamically when they can.

From my standpoint there is no security issue here, as each encryption session gets new session key, so transferring will be impossible. And replay will not be possible due to amount of private keys highly exceeding the amount of group keys (like 1000 times more for each generation). So it is not important whether Apple authorises its own computer or not, private keys will unlikely much even with ten different machines of the same mac model.

To my eyes, the issue with this not working is not really about PAVP not understanding stuff, but rather PAVP not being initialised properly, as it freezes at any video playback, even non-DRM.

@osy
Copy link

osy commented Dec 3, 2019

Right, but from my (< 2 hours) research into EPID/DAA protocol, there is 1 unique private key but the corresponding public key is shared by all members of the group.

An EPID private key has one corresponding EPID public key—the group public key. However, a group public key corresponds to multiple EPID private keys. The number of private keys that map to the same group public key is configurable; it can be as few as several hundred or as many as tens of millions. Obviously, a group with more members, in theory, features better anonymity and offers more privacy.

So in order for Apple's group public key to work, the EPID authority that generated the private key must be the same one that Apple uses. I'm not saying this is definitely not true, but I would be surprised if it is true.

There are likely other issues in the way too resulting in video playback failing, but my point is that IF iTunes DRM depends on the EPID (which it could very well not, and only depend on a provisioned status) AND the EPID authority for Apple is different (which is probably is), then there's no way to ever get it working (even if all other problems are resolved).

Decrypted ME 12 firmware containing Apple specific stuff, group key blobs containing basically all keys, flashed stock chipsets on MacBooks, and ME gladly accepting Apple certificate all that evidence imply that Apple supports all private keys

I don't see that as evidence for Apple having a EPID public key that works for your chipset. The private key is stored in fuses and cannot be changed. If you flashed Apple certificates, the only time an error will show up is when you try to provision the public key and it fails the signature validation.

So with the code in [9], what actually happens when you try to provision with an Apple public key (assuming they have one with your group number)? Is it an error?

EDIT: In response to

Intel does not let anybody meddle with its rights as an authority, so private keys fused during the manufacturing process are basically random, and should be no different for Apple and non-Apple hardware.

I believe OEMs are allowed to program their own ME fuses. Probably not all fuses though.

@vit9696
Copy link
Contributor Author

vit9696 commented Dec 3, 2019

So in order for Apple's group public key to work, the EPID authority that generated the private key must be the same one that Apple uses. I'm not saying this is definitely not true, but I would be surprised if it is true.

iTunes DRM does depend on EPID when IGPU is used, yes, this is certain. I did some reverse engineering in the past and figured that much. This is called com.apple.fps.2_X or com.apple.fps.3_X and implemented as AVFoundation private media source. Some vendors, such as Netflix, require FairPlay 2+, which can only work with hardware assistance (IGPU with EPID or AMD GPU). Apple itself for iTunes requires FairPlay 1+, but uses newest available, unless we forcibly claim we do not support 2+ (that's what WhateverGreen does).

I don't see that as evidence for Apple having a EPID public key that works for your chipset. The private key is stored in fuses and cannot be changed. If you flashed Apple certificates, the only time an error will show up is when you try to provision the public key and it fails the signature validation.

So with the code in [9], what actually happens when you try to provision with an Apple public key (assuming they have one with your group number)? Is it an error?

So far all group keys returned by hardware (we tried 4 machines as you see) were found in Apple firmwares (each firmware supports a large number of group key ids). ME accepted that key and returned success. So indeed Apple certificate was created to work with these keys. This is how it looked basically (slightly older code):

00:598 00:035 OC: Starting EPID provisioning
00:633 00:034 OC: IGPU is 4128086
00:668 00:035 OC: Needs provisioning EPID - Success
00:706 00:038 OC: HECI protocol lookup - Success
00:748 00:041 OC: No D1A26C1F-ABF5-4806-BB24-68D317E071D5 in firmware, using default - Not Found
00:784 00:036 OC: No 2906CC1F-09CA-4457-9A4F-C212C545D3D3 in firmware, using default - Not Found
00:820 00:035 OC: Provisioning data - Success
00:857 00:036 OC: Got 8 clients - Success
00:894 00:036 OC: Client 0 has 55213584-9A29-4916-BADF-0FB7ED682AEB protocol - Success
00:955 00:061 OC: Client 1 has 309DCDE8-CCB1-4062-8F78-600115A34327 protocol - Success
00:993 00:037 OC: Client 2 has 8E6A6715-9ABC-4043-88EF-9E39C6F63E0F protocol - Success
01:031 00:038 OC: Client 3 has 8C2F4425-77D6-4755-ACA3-891FDBC66A58 protocol - Success
01:069 00:037 OC: Client 4 has F908627D-13BF-4A04-B91F-A64E9245323D protocol - Success
01:105 00:036 OC: Client 5 has 3C4852D6-D47B-4F46-B05E-B5EDC1AA440E protocol - Success
01:143 00:037 OC: Client 6 has FBF6FCF1-96CF-4E2E-A6A6-1BAB8CBE36B1 protocol - Success
01:178 00:035 OC: Found application at 6
01:220 00:041 OC: Connect to client 25 code 0 - Success
02:774 01:553 OC: Got EPID status 2 and key 4DF - Success
02:809 00:035 OC: Got EPID group public key - Success
03:318 00:508 OC: Finished provisioning command with status 0 - Success
03:357 00:039 OC: Sent EPID certificate - Success
03:396 00:038 OC: Disconnect from client 25 code 0 - Success
03:431 00:035 OC: Done EPID provisioning - Success

Afterwards it will report "successfully provisioned:

01:690 01:513 OC: Got EPID status 0 and key 4DF - Success

The keys we got were 0x4DF (ASUS Z87 board), 0x4E0 (GIGABYTE Z87 board), 0x6AD (ASUS Haswell laptop), 0x37F (Dell Ivy Bridge board).

I believe OEMs are allowed to program their own ME fuses. Probably not all fuses though.

They can, yes, but hardly anybody does it.

@osy
Copy link

osy commented Dec 3, 2019

I see, that's good to know. So the current status is: EPID can be provisioned, but PAVP still does not work? Can you post relevant error logs when iTunes DRM protected content is played?

@vit9696
Copy link
Contributor Author

vit9696 commented Dec 3, 2019

EPID can be provisioned, but PAVP still does not work?

Pretty much.

Can you post relevant error logs when iTunes DRM protected content is played?

I can, but there is not much there. Apple killed most of things starting with 10.12 or 10.13. Formerly you could enable debugging with fp_trace, and there was a lot of good stuff MediaToolBox and AppleGVA, as explained in Shiki FAQ. The easiest to test it is by playing an encrypted QuickTime trailer (also linked in the FAQ). I could share some legacy idbs I guess.

@vit9696
Copy link
Contributor Author

vit9696 commented Dec 8, 2019

Regarding software decoder, I actually discovered that TV+ can use same old FP1, so it is possible to run it in software. I was unable to properly disable IGPU from being forcibly used so far for this type of media (encv), however, so the patches only work with IGPU disabled in firmware. Help appreciated :)

@osy
Copy link

osy commented Jan 11, 2020

I spent some time on this and I'll report some of my findings here.

On my build, when attempting to load IGPU without any WG patches, I get the following log

2020-01-10 16:47:13.582853-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Begin Gfx firmware load process
2020-01-10 16:47:13.597301-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    ForceWake Multithread = 0x30002
2020-01-10 16:47:13.612105-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    CONFIG0 (0xD00)       = 0x80000000
2020-01-10 16:47:13.625414-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    GT_THREAD_STATUS      = 0x400b0000
2020-01-10 16:47:13.652595-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    Doing retry #0
2020-01-10 16:47:15.511865-0800 0x473      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Hash data from ME never returned, status = 1, doing retry #1

By tracing IGGuC::loadBinary(bool) we find that it is polling on a register (0xc0f4) and waiting for a specific result of 0x1ff

                    uVar10 = *(uint *)(lVar13 + 0xc0f4);
                    puVar25 = (undefined *)(ulong)uVar10;
                    bVar26 = SUB41(uVar10,0);
                    if (uVar10 == 0x1ff) {
                      this_01 = (long *)(this_00 + 0x1208);
                      if ((local_54 & 1) != 0) {
                        *(int *)(this + 0x490) = local_64;
                        local_54 = 0;
                      }
                      goto start_xfer;
                    }

From my understanding of how ME interfaces with the CPU, it doesn't seem like there's a way for the ME to enforce any security in GuC loading. For that to work, the ME would have to sit in between the data path from the CPU to the IGPU or somehow there would be a three-way handshake. However, looking at the Linux source, that does not appear to be the case.

So it is likely the case that OSX is the one that checks the ME, which makes the message "Hash data from ME never returned" seem more reasonable.

From there, I tried to patch out the ME checks and got farther in the GuC load process

2020-01-10 22:40:15.765226-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Begin Gfx firmware load process
2020-01-10 22:40:15.778575-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    ForceWake Multithread = 0x30002
2020-01-10 22:40:15.791577-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    CONFIG0 (0xD00)       = 0x80000000
2020-01-10 22:40:15.804474-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    GT_THREAD_STATUS      = 0x400b000
2020-01-10 22:40:15.816963-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU]    Doing retry #0
2020-01-10 22:40:17.609575-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Graphics Firmware Version: 0.0.0.0
2020-01-10 22:40:17.609734-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] SBErrorMsg         : 0x4047a000
2020-01-10 22:40:17.610221-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Failed to load graphics firmware binary, STATUS = 0x870000EC
2020-01-10 22:40:17.623438-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Failed to initialize graphics firmware.
2020-01-10 22:40:17.623600-0800 0x476      Default     0x0                  0      0    kernel: (AppleIntelKBLGraphics) [IGPU] Failed to start graphics engine

The status register 0x870000EC is actually documented in Linux kernel. We observe that from the given status that we got GS_AUTH_STATUS_GOOD and GS_BOOTROM_JUMP_PASSED but we did not get GS_UKERNEL_READY which is what the OSX code looks for in order to pass loadBinary. (Linux also looks for this condition). This means that Springboard was authenticated but failed with some undocumented error code (0x4047a000) in the scratch register.

I would be curious if the error is due to some configuration issues (not enabling PAVP, no stolen memory, etc) and if this error code is unique (I found zero results on Google). My next test will be to see if I can get a different error code after provisioning PAVP.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 11, 2020

Hi, now that you mentioned it, I think I did exactly the same thing in older operating system versions. Indeed, Linux kernel does not document this code, we found no other firmware that does.

We searched for any information regarding GuC firmware, and found some references that it is legacy OEM firmware introduced before GuC. I remember that it can actually be encrypted, and unlike the default Linux firmware, extra provisioning may be needed for this firmware to work. We failed to find any GuC keys in Apple firmwares though.

As for authentication, is not GuC firmware executed on ME processor?

@osy
Copy link

osy commented Jan 11, 2020

The GuC runs its own processor.

@osy
Copy link

osy commented Jan 12, 2020

PAVP config

The PAVPC register is in PCI config for host bridge (offset 58h) as well as the MMIO config space for IGPU (offset 1082C0h). This is defined in vol 2 of the Kaby Lake H datasheet and afaik the IGPU registers are a mirror of the host bridge ones.

Screen Shot 2020-01-11 at 8 05 32 PM

On my I7-8809G machine, the register is read to be 0x7FF00047 but on the Mac it is 0x7FF00017. The only difference is on the Mac, bit 4 is set and bit 6 is not set. In EFI PlatformInit, the Mac explicitly enables bit 4 only when booting into OSX. Bit 6 is never set.

Additionally, on the Mac, when booting into OSX, and after setting up the IGPU will poll GEN6_GT_CORE_STATUS and then write to a series of registers 0x320F4, 0x1229C, 0x320F0.

Those seems to be the only difference in the IGPU init code between my BIOS and the Kabylake Mac BIOS. Unfortunately because my BIOS locked the register (and has BIOS Guard and Boot Guard), I cannot test any modifications. I would be curious to see if setting the bits the same as the Mac would do anything.

Provisioning

I had to make some modifications to get the HECI interface to work. Seems like the protocol has been updated in Skylake and beyond (haven't checked any earlier). However, it seems like by group id is not supported and Intel has already provisioned the IGPU from BIOS so it cannot be re-provisioned anyways. Here is my log

00:104 00:000 OC: Starting EPID provisioning
00:104 00:000 OC: IGPU is 591B8086
00:104 00:000 OC: Needs provisioning EPID - Success
00:104 00:000 OC: HECI protocol lookup - Success
00:106 00:002 OC: No D1A26C1F-ABF5-4806-BB24-68D317E071D5 in firmware, using default - Not Found
00:108 00:002 OC: No 2906CC1F-09CA-4457-9A4F-C212C545D3D3 in firmware, using default - Not Found
00:108 00:000 OC: Provisioning data - Success
00:111 00:002 OC: Got 13 clients - Success
00:112 00:001 OC: Client 0 has 55213584-9A29-4916-BADF-0FB7ED682AEB protocol - Success
00:114 00:001 OC: Client 1 has 42B3CE2F-BD9F-485A-96AE-26406230B1FF protocol - Success
00:115 00:001 OC: Client 2 has 01E88543-8050-4380-9D6F-4F9CEC704917 protocol - Success
00:117 00:001 OC: Client 3 has 8E6A6715-9ABC-4043-88EF-9E39C6F63E0F protocol - Success
00:118 00:001 OC: Client 4 has 8C2F4425-77D6-4755-ACA3-891FDBC66A58 protocol - Success
00:120 00:001 OC: Client 5 has 309DCDE8-CCB1-4062-8F78-600115A34327 protocol - Success
00:121 00:001 OC: Client 6 has F908627D-13BF-4A04-B91F-A64E9245323D protocol - Success
00:123 00:001 OC: Client 7 has DBA4D603-D7ED-4931-8823-17AD585705D5 protocol - Success
00:124 00:001 OC: Client 8 has 5565A099-7FE2-45C1-A22B-D7E9DFEA9A2E protocol - Success
00:126 00:001 OC: Client 9 has 3C4852D6-D47B-4F46-B05E-B5EDC1AA440E protocol - Success
00:127 00:001 OC: Client 10 has 082EE5A7-7C25-470A-9643-0C06F0466EA1 protocol - Success
00:129 00:001 OC: Client 11 has FBF6FCF1-96CF-4E2E-A6A6-1BAB8CBE36B1 protocol - Success
00:129 00:000 OC: Found application at 11
00:132 00:002 OC: Connect to client 28 code 0 - Success
00:192 00:060 OC: Got EPID status 0 and group id 2024 - Success
00:192 00:000 OC: Got EPID group public key - Not Found
00:194 00:002 OC: Disconnect from client 28 code 0 - Success
00:195 00:000 OC: Done EPID provisioning - Not Found

Anyways I think that's as much as I can do since I don't have another system to test with and it is pretty locked down on this one.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 12, 2020

Thanks for the research. I am not positive we can do much, but we will test it on some machines later and let you know if we find any good one.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 12, 2020

Ok, we tested it on ASUS Z170M-Plus, and got the following results.

00:191 00:006 OC: 00:197 00:005 OC: Current PAVPC is B7F00047
00:202 00:004 OC: Starting EPID provisioning
00:206 00:004 OC: IGPU is 19128086
00:211 00:004 OC: Needs provisioning EPID - Success
00:216 00:004 OCME: Falling back to HECI 2 protocol - Not Found
00:220 00:004 OC: HECI protocol lookup - Success
00:228 00:007 OCME: No D1A26C1F-ABF5-4806-BB24-68D317E071D5 in firmware, using default - Not Found
00:236 00:007 OCME: No 2906CC1F-09CA-4457-9A4F-C212C545D3D3 in firmware, using default - Not Found
00:240 00:004 OC: Provisioning data - Success
00:247 00:006 OC: Got 13 clients - Success
00:254 00:006 OC: Client 0 has 55213584-9A29-4916-BADF-0FB7ED682AEB protocol - Success
00:264 00:009 OC: Client 1 has 42B3CE2F-BD9F-485A-96AE-26406230B1FF protocol - Success
00:271 00:007 OC: Client 2 has 01E88543-8050-4380-9D6F-4F9CEC704917 protocol - Success
00:278 00:006 OC: Client 3 has 8E6A6715-9ABC-4043-88EF-9E39C6F63E0F protocol - Success
00:287 00:008 OC: Client 4 has 8C2F4425-77D6-4755-ACA3-891FDBC66A58 protocol - Success
00:294 00:006 OC: Client 5 has 309DCDE8-CCB1-4062-8F78-600115A34327 protocol - Success
00:301 00:006 OC: Client 6 has F908627D-13BF-4A04-B91F-A64E9245323D protocol - Success
00:308 00:006 OC: Client 7 has DBA4D603-D7ED-4931-8823-17AD585705D5 protocol - Success
00:315 00:006 OC: Client 8 has 5565A099-7FE2-45C1-A22B-D7E9DFEA9A2E protocol - Success
00:322 00:007 OC: Client 9 has 3C4852D6-D47B-4F46-B05E-B5EDC1AA440E protocol - Success
00:328 00:006 OC: Client 10 has 082EE5A7-7C25-470A-9643-0C06F0466EA1 protocol - Success
00:335 00:006 OC: Client 11 has FBF6FCF1-96CF-4E2E-A6A6-1BAB8CBE36B1 protocol - Success
00:340 00:004 OC: Found application at 11
00:348 00:007 OCME: Connect to client 28 code 0 - Success
00:436 00:087 OC: Got EPID status 0 and group id 1FAF - Success
00:444 00:007 OC: Disconnect from client 28 code 0 - Success
00:448 00:004 OC: Done EPID provisioning - Success

PAVPC on Skylake is also locked, and provisioning is also done. It is likely that this group id key can be found in newer Apple firmwares, but resetting the provisioning and changing PAVPC values will require firmware modifications anyway. We could try this on Haswell, where we have more control, but the overall idea does not sound very promising in such state.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 12, 2020

I also moved the code to master into OcHeciLib / PavpProvision, so that one can play with this later if he wants (https://github.com/acidanthera/OcSupportPkg/tree/master/Application/PavpProvision).

@osy
Copy link

osy commented Jan 12, 2020

The group ids in ProvisionData.c are 0x4db, 0x4dc, 0x69a-0x829.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 12, 2020

Yes, that was dumped from a Haswell machine, if you dump the same file from a newer machine, it will contain higher IDs. Basically the values increase as the generation increases.

@osy
Copy link

osy commented Jan 13, 2020

Seems like Kabylake macs have 0xf81-0x1110. Coffeelake macs have 0x28af-0x2a3e. I wasn't able to find 0x1faf or 0x2024 anywhere in any of the firmware packages in the OSX updater.

@vit9696
Copy link
Contributor Author

vit9696 commented Jan 13, 2020

Wow, that is worrying. So in these days they even have separate group id ranges. In this case it may be beneficial to invest in porting GuC from Linux, that will at least fix the IGPU performance issues.

As for DRM, I somehow get a feeling it is a dead end with recent Intel generations. While it is likely that generic chipsets with GIDs from Macs do exist, the fact that many if not all chipsets are provisioned and have incompatible GIDs pretty much defeats the research purpose in this direction. Perhaps, we should invest in getting AMD decoder to work and/or enabling software decoder.

@vit9696
Copy link
Contributor Author

vit9696 commented Mar 24, 2020

We confirmed testing that GuC firmwares successfully load on 9th generation mobile chipsets and newer, e.g. on Dell Inspiron 7590 with Core i7-9750H. To do this one can use igfxfw=2 boot-argument or inject igfxfw = <02 00 00 00> property into IGPU (preferred).

PAVP/HDCP is still broken (causes cursor stuttering and lags during video playback). PAVP provisioning is also not possible, as the key is already provisioned:

00:000 00:000 OCPAVP: Checking PAVPC register...
00:004 00:004 OCPAVP: Current PAVPC is 7F700047
00:007 00:003 OCPAVP: Starting EPID provisioning
00:010 00:003 OCPAVP: IGPU is 3E9B8086
00:014 00:003 OCPAVP: Needs provisioning EPID - Success
00:017 00:003 OCME: Falling back to HECI 2 protocol - Not Found
00:020 00:003 OCPAVP: HECI protocol lookup - Success
00:027 00:006 OCME: No D1A26C1F-ABF5-4806-BB24-68D317E071D5 in firmware, using default - Not Found
00:033 00:006 OCME: No 2906CC1F-09CA-4457-9A4F-C212C545D3D3 in firmware, using default - Not Found
00:036 00:003 OCPAVP: Provisioning data - Success
00:051 00:014 OCPAVP: Got 13 clients - Success
00:056 00:004 OCPAVP: Client 0 has 4FCC395C-A9E5-4647-BC68-47BAD7CC6BD3 protocol - Success
00:064 00:007 OCPAVP: Client 1 has 55213584-9A29-4916-BADF-0FB7ED682AEB protocol - Success
00:068 00:004 OCPAVP: Client 2 has 42B3CE2F-BD9F-485A-96AE-26406230B1FF protocol - Success
00:074 00:005 OCPAVP: Client 3 has 8E6A6715-9ABC-4043-88EF-9E39C6F63E0F protocol - Success
00:081 00:007 OCPAVP: Client 4 has 8C2F4425-77D6-4755-ACA3-891FDBC66A58 protocol - Success
00:086 00:004 OCPAVP: Client 5 has 309DCDE8-CCB1-4062-8F78-600115A34327 protocol - Success
00:091 00:004 OCPAVP: Client 6 has F908627D-13BF-4A04-B91F-A64E9245323D protocol - Success
00:096 00:004 OCPAVP: Client 7 has DBA4D603-D7ED-4931-8823-17AD585705D5 protocol - Success
00:101 00:005 OCPAVP: Client 8 has 5565A099-7FE2-45C1-A22B-D7E9DFEA9A2E protocol - Success
00:105 00:004 OCPAVP: Client 9 has 082EE5A7-7C25-470A-9643-0C06F0466EA1 protocol - Success
00:110 00:004 OCPAVP: Client 10 has 3C4852D6-D47B-4F46-B05E-B5EDC1AA440E protocol - Success
00:115 00:004 OCPAVP: Client 11 has FBF6FCF1-96CF-4E2E-A6A6-1BAB8CBE36B1 protocol - Success
00:118 00:003 OCPAVP: Found application at 11
00:124 00:006 OCME: Connect to client 28 code 0 - Success
00:242 00:117 OCPAVP: Got EPID status 0 and group id 28E7 - Success
00:247 00:005 OCME: Disconnect from client 28 code 0 - Success
00:251 00:003 OCPAVP: Done EPID provisioning - Success

Interestingly, this key is present in MacBookPro15,x+ firmwares, so if it was possible to reprovision by e.g. cleaning ME region, PAVP may have worked. Still, this is better than nothing, and probably the maximum we can achieve. Closing as resolved (to some level).

REF: #748

@wolf606
Copy link

wolf606 commented Jun 5, 2024

How did we come up with the fact that 'GuC firmware will only load on 14nm chipsets'? Isn't the GuC firmware loaded on the iGPU coprocessor? And if that is truly the case, what is the behavior on Skylake chipsets on real Macs? Are these 14nm chipsets? Or is it an older node size and it resorts to using the host scheduler?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Development

No branches or pull requests

3 participants