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

make System.Security.Cryptography.X509Certificates compliant with interop guidelines - part 3 #61435

Merged
merged 2 commits into from
Nov 22, 2021

Conversation

pedrobsaila
Copy link
Contributor

@pedrobsaila pedrobsaila commented Nov 10, 2021

Fixes partially #51564

The issue is still under progress, more PRs are to come. The current one makes the following calls compliant with Interop guidelines :

  • Crypt32.CryptDecodeObjectPointer
  • Crypt32.CertCreateCertificateChainEngine
  • Crypt32.CertFreeCertificateChainEngine
  • Crypt32.CertGetCertificateChain
  • Crypt32.CryptHashPublicKeyInfo
  • Crypt32.CertSaveStore
  • Crypt32.CertFindCertificateInStore
  • Crypt32.CertVerifyTimeValidity
  • Crypt32.CertFindExtension
  • Crypt32.CertGetIntendedKeyUsage
  • Crypt32.CertGetValidUsages
  • Crypt32.CertControlStore
  • Crypt32.CertDeleteCertificateFromStore
  • Crypt32.CertFreeCertificateChain
  • Crypt32.CertGetIntendedKeyUsage
  • Crypt32.CertVerifyCertificateChainPolicy
  • Crypt32.CryptImportPublicKeyInfoEx2
  • Crypt32.CertVerifyCertificateChainPolicy
  • Crypt32.CryptAcquireCertificatePrivateKey
  • Advapi32.CryptAcquireContext

There are 5 DllImport methods inside System.Security.Cryptography.X509Certificates.Tests project, should I move them also ?

@ghost ghost added the community-contribution Indicates that the PR has been added by a community member label Nov 10, 2021
@ghost
Copy link

ghost commented Nov 10, 2021

Tagging subscribers to this area: @bartonjs, @vcsjones, @krwq, @GrabYourPitchforks
See info in area-owners.md if you want to be subscribed.

Issue Details

Fixes #51564

This PR makes the following calls compliant with Interop gudielines :

  • Crypt32.CryptDecodeObjectPointer
  • Crypt32.CertCreateCertificateChainEngine
  • Crypt32.CertFreeCertificateChainEngine
  • Crypt32.CertGetCertificateChain
  • Crypt32.CryptHashPublicKeyInfo
  • Crypt32.CertSaveStore
  • Crypt32.CertFindCertificateInStore
  • Crypt32.CertVerifyTimeValidity
  • Crypt32.CertFindExtension
  • Crypt32.CertGetIntendedKeyUsage
  • Crypt32.CertGetValidUsages
  • Crypt32.CertControlStore
  • Crypt32.CertDeleteCertificateFromStore
  • Crypt32.CertFreeCertificateChain
  • Crypt32.CertGetIntendedKeyUsage
  • Crypt32.CertVerifyCertificateChainPolicy
  • Crypt32.CryptImportPublicKeyInfoEx2
  • Crypt32.CertVerifyCertificateChainPolicy
  • Crypt32.CryptAcquireCertificatePrivateKey
  • Advapi32.CryptAcquireContext

There's 5 Interop calls inside System.Security.Cryptography.X509Certificates.Tests project, should I move them also or it is OK for DllImport to be in test libraries?

Author: pedrobsaila
Assignees: -
Labels:

area-System.Security

Milestone: -

{
[GeneratedDllImport(Libraries.Advapi32, EntryPoint = "CryptAcquireContextW", CharSet = CharSet.Unicode, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
public static unsafe partial bool CryptAcquireContext(out IntPtr psafeProvHandle, char* pszContainer, char* pszProvider, int dwProvType, Crypt32.CryptAcquireContextFlags dwFlags);
internal static unsafe partial bool CryptAcquireContext(out IntPtr psafeProvHandle,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CryptAcquireContext(out IntPtr psafeProvHandle,
internal static unsafe partial bool CryptAcquireContext(
out IntPtr psafeProvHandle,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, SetLastError = true)]
internal static unsafe partial bool CertGetCertificateChain(IntPtr hChainEngine,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Personally, I'd put all of the contents of CERT_CHAIN_PARA.cs into this file, since there's no need for it with any other function.

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, SetLastError = true)]
internal static unsafe partial bool CertGetCertificateChain(IntPtr hChainEngine,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CertGetCertificateChain(IntPtr hChainEngine,
internal static unsafe partial bool CertGetCertificateChain(
IntPtr hChainEngine,

// Note: It's somewhat unusual to use an API enum as a parameter type to a P/Invoke but in this case, X509KeyUsageFlags was intentionally designed as bit-wise
// identical to the wincrypt CERT_*_USAGE values.
[GeneratedDllImport(Libraries.Crypt32, CharSet = CharSet.Unicode, SetLastError = true)]
internal static unsafe partial bool CertGetIntendedKeyUsage(CertEncodingType dwCertEncodingType,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CertGetIntendedKeyUsage(CertEncodingType dwCertEncodingType,
internal static unsafe partial bool CertGetIntendedKeyUsage(
CertEncodingType dwCertEncodingType,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, CharSet = CharSet.Unicode, SetLastError = true)]
internal static unsafe partial SafeCertContextHandle CertFindCertificateInStore(SafeCertStoreHandle hCertStore,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial SafeCertContextHandle CertFindCertificateInStore(SafeCertStoreHandle hCertStore,
internal static unsafe partial SafeCertContextHandle CertFindCertificateInStore(
SafeCertStoreHandle hCertStore,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, CharSet = CharSet.Unicode, SetLastError = true)]
public static partial bool CryptAcquireCertificatePrivateKey(SafeCertContextHandle pCert,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
public static partial bool CryptAcquireCertificatePrivateKey(SafeCertContextHandle pCert,
public static partial bool CryptAcquireCertificatePrivateKey(
SafeCertContextHandle pCert,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, EntryPoint = "CryptDecodeObject", CharSet = CharSet.Unicode, SetLastError = true)]
internal static unsafe partial bool CryptDecodeObjectPointer(CertEncodingType dwCertEncodingType,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CryptDecodeObjectPointer(CertEncodingType dwCertEncodingType,
internal static unsafe partial bool CryptDecodeObjectPointer(
CertEncodingType dwCertEncodingType,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, EntryPoint = "CryptDecodeObject", CharSet = CharSet.Unicode, SetLastError = true)]
internal static unsafe partial bool CryptDecodeObjectPointer(CertEncodingType dwCertEncodingType,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CryptDecodeObjectPointer(CertEncodingType dwCertEncodingType,
internal static unsafe partial bool CryptDecodeObjectPointer(
CertEncodingType dwCertEncodingType,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, CharSet = CharSet.Unicode, SetLastError = true)]
internal static partial bool CryptHashPublicKeyInfo(IntPtr hCryptProv,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static partial bool CryptHashPublicKeyInfo(IntPtr hCryptProv,
internal static partial bool CryptHashPublicKeyInfo(
IntPtr hCryptProv,

internal static partial class Crypt32
{
[GeneratedDllImport(Libraries.Crypt32, CharSet = CharSet.Unicode, SetLastError = true)]
internal static unsafe partial bool CryptImportPublicKeyInfoEx2(CertEncodingType dwCertEncodingType,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
internal static unsafe partial bool CryptImportPublicKeyInfoEx2(CertEncodingType dwCertEncodingType,
internal static unsafe partial bool CryptImportPublicKeyInfoEx2(
CertEncodingType dwCertEncodingType,

@bartonjs
Copy link
Member

There are 5 DllImport methods inside System.Security.Cryptography.X509Certificates.Tests project, should I move them also ?

Search-fu is failing me today. What are they?

@pedrobsaila
Copy link
Contributor Author

Search-fu is failing me today. What are they?

[DllImport(Interop.Libraries.CryptoNative, EntryPoint = "CryptoNative_CheckX509Hostname")]
private static extern int CheckX509Hostname(IntPtr x509, string hostname, int cchHostname);

[DllImport("crypt32.dll", CharSet = CharSet.Unicode, SetLastError = true)]
private static extern bool CryptQueryObject(
CertQueryObjectType dwObjectType,
[In] ref CRYPTOAPI_BLOB pvObject,
ExpectedContentTypeFlags dwExpectedContentTypeFlags,
ExpectedFormatTypeFlags dwExpectedFormatTypeFlags,
int dwFlags, // reserved - always pass 0
IntPtr pdwMsgAndCertEncodingType,
IntPtr pdwContentType,
IntPtr pdwFormatType,
IntPtr phCertStore,
IntPtr phMsg,
out IntPtr ppvContext
);
[DllImport("crypt32.dll", CharSet = CharSet.Unicode, SetLastError = true)]
private static extern bool CertFreeCertificateContext(IntPtr pCertContext);

[DllImport("libc")]
private static extern int chmod(string path, int mode);
[DllImport("libc")]
private static extern uint geteuid();

@bartonjs
Copy link
Member

Hm. I'm guessing that the tests had their own P/Invokes because they were originally compiled as AnyOS.

Since they're split now (and the in-progress unified System.Security.Cryptography.Tests is already split) they should probably be fixed to use the existing interop-decls. (CheckX509Hostname being the hardest of the three, since the Interop decl uses a SafeHandle instead of IntPtr and is in a grab-bag file... so for that one it's probably just making a dedicated Interop.CheckX509Hostname for the IntPtr version and leaving the SafeHandle version where it is). -- But that should be a followup PR, no need to reset this one 😄

@bartonjs bartonjs merged commit c334e55 into dotnet:main Nov 22, 2021
@bartonjs
Copy link
Member

Thanks for doing this, @pedrobsaila!

شكرا & merci

@pedrobsaila pedrobsaila deleted the 51564/part4 branch November 22, 2021 18:30
@ghost ghost locked as resolved and limited conversation to collaborators Dec 22, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
area-System.Security community-contribution Indicates that the PR has been added by a community member
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants