1 // Licensed to the .NET Foundation under one or more agreements.
2 // The .NET Foundation licenses this file to you under the MIT license.
3 // See the LICENSE file in the project root for more information.
4 
5 using System;
6 using System.Runtime.InteropServices;
7 using System.Security.Cryptography;
8 using System.Security.Cryptography.X509Certificates;
9 using Microsoft.Win32.SafeHandles;
10 
11 internal static partial class Interop
12 {
13     internal static partial class Crypto
14     {
X509StoreVerifyCallback(int ok, IntPtr ctx)15         internal delegate int X509StoreVerifyCallback(int ok, IntPtr ctx);
16 
17         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509EvpPublicKey")]
GetX509EvpPublicKey(SafeX509Handle x509)18         internal static extern SafeEvpPKeyHandle GetX509EvpPublicKey(SafeX509Handle x509);
19 
20         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_DecodeX509Crl")]
DecodeX509Crl(byte[] buf, int len)21         internal static extern SafeX509CrlHandle DecodeX509Crl(byte[] buf, int len);
22 
23         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_DecodeX509")]
DecodeX509(byte[] buf, int len)24         internal static extern SafeX509Handle DecodeX509(byte[] buf, int len);
25 
26         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509DerSize")]
GetX509DerSize(SafeX509Handle x)27         internal static extern int GetX509DerSize(SafeX509Handle x);
28 
29         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_EncodeX509")]
EncodeX509(SafeX509Handle x, byte[] buf)30         internal static extern int EncodeX509(SafeX509Handle x, byte[] buf);
31 
32         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509Destroy")]
X509Destroy(IntPtr a)33         internal static extern void X509Destroy(IntPtr a);
34 
35         /// <summary>
36         /// Clone the input certificate into a new object.
37         /// </summary>
38         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509Duplicate")]
X509Duplicate(IntPtr handle)39         internal static extern SafeX509Handle X509Duplicate(IntPtr handle);
40 
41         /// <summary>
42         /// Clone the input certificate into a new object.
43         /// </summary>
44         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509Duplicate")]
X509Duplicate(SafeX509Handle handle)45         internal static extern SafeX509Handle X509Duplicate(SafeX509Handle handle);
46 
47         /// <summary>
48         /// Increment the native reference count of the certificate to protect against
49         /// a free from another pointer-holder.
50         /// </summary>
51         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509UpRef")]
X509UpRef(IntPtr handle)52         internal static extern SafeX509Handle X509UpRef(IntPtr handle);
53 
54         /// <summary>
55         /// Increment the native reference count of the certificate to protect against
56         /// a free from another pointer-holder.
57         /// </summary>
58         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509UpRef")]
X509UpRef(SafeX509Handle handle)59         internal static extern SafeX509Handle X509UpRef(SafeX509Handle handle);
60 
61         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_PemReadX509FromBio")]
PemReadX509FromBio(SafeBioHandle bio)62         internal static extern SafeX509Handle PemReadX509FromBio(SafeBioHandle bio);
63 
64         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509GetSerialNumber")]
X509GetSerialNumber_private(SafeX509Handle x)65         private static extern SafeSharedAsn1IntegerHandle X509GetSerialNumber_private(SafeX509Handle x);
66 
X509GetSerialNumber(SafeX509Handle x)67         internal static SafeSharedAsn1IntegerHandle X509GetSerialNumber(SafeX509Handle x)
68         {
69             CheckValidOpenSslHandle(x);
70 
71             return SafeInteriorHandle.OpenInteriorHandle(
72                 handle => X509GetSerialNumber_private(handle),
73                 x);
74         }
75 
76         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509GetIssuerName")]
X509GetIssuerName(SafeX509Handle x)77         internal static extern IntPtr X509GetIssuerName(SafeX509Handle x);
78 
79         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509GetSubjectName")]
X509GetSubjectName(SafeX509Handle x)80         internal static extern IntPtr X509GetSubjectName(SafeX509Handle x);
81 
82         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509CheckPurpose")]
83         [return: MarshalAs(UnmanagedType.Bool)]
X509CheckPurpose(SafeX509Handle x, int id, int ca)84         internal static extern bool X509CheckPurpose(SafeX509Handle x, int id, int ca);
85 
86         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509CheckIssued")]
X509CheckIssued(SafeX509Handle issuer, SafeX509Handle subject)87         internal static extern int X509CheckIssued(SafeX509Handle issuer, SafeX509Handle subject);
88 
89         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509IssuerNameHash")]
X509IssuerNameHash(SafeX509Handle x)90         internal static extern ulong X509IssuerNameHash(SafeX509Handle x);
91 
92         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509GetExtCount")]
X509GetExtCount(SafeX509Handle x)93         internal static extern int X509GetExtCount(SafeX509Handle x);
94 
95         // Returns a pointer already being tracked by the SafeX509Handle, shouldn't be SafeHandle tracked/freed.
96         // Bounds checking is in place for "loc", IntPtr.Zero is returned on violations.
97         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509GetExt")]
X509GetExt(SafeX509Handle x, int loc)98         internal static extern IntPtr X509GetExt(SafeX509Handle x, int loc);
99 
100         // Returns a pointer already being tracked by a SafeX509Handle, shouldn't be SafeHandle tracked/freed.
101         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509ExtensionGetOid")]
X509ExtensionGetOid(IntPtr ex)102         internal static extern IntPtr X509ExtensionGetOid(IntPtr ex);
103 
104         // Returns a pointer already being tracked by a SafeX509Handle, shouldn't be SafeHandle tracked/freed.
105         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509ExtensionGetData")]
X509ExtensionGetData(IntPtr ex)106         internal static extern IntPtr X509ExtensionGetData(IntPtr ex);
107 
108         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509ExtensionGetCritical")]
109         [return: MarshalAs(UnmanagedType.Bool)]
X509ExtensionGetCritical(IntPtr ex)110         internal static extern bool X509ExtensionGetCritical(IntPtr ex);
111 
112         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreCreate")]
X509StoreCreate()113         internal static extern SafeX509StoreHandle X509StoreCreate();
114 
115         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreDestory")]
X509StoreDestory(IntPtr v)116         internal static extern void X509StoreDestory(IntPtr v);
117 
118         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreAddCert")]
119         [return: MarshalAs(UnmanagedType.Bool)]
X509StoreAddCert(SafeX509StoreHandle ctx, SafeX509Handle x)120         internal static extern bool X509StoreAddCert(SafeX509StoreHandle ctx, SafeX509Handle x);
121 
122         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreAddCrl")]
123         [return: MarshalAs(UnmanagedType.Bool)]
X509StoreAddCrl(SafeX509StoreHandle ctx, SafeX509CrlHandle x)124         internal static extern bool X509StoreAddCrl(SafeX509StoreHandle ctx, SafeX509CrlHandle x);
125 
126         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreSetRevocationFlag")]
127         [return: MarshalAs(UnmanagedType.Bool)]
X509StoreSetRevocationFlag(SafeX509StoreHandle ctx, X509RevocationFlag revocationFlag)128         internal static extern bool X509StoreSetRevocationFlag(SafeX509StoreHandle ctx, X509RevocationFlag revocationFlag);
129 
130         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreCtxInit")]
131         [return: MarshalAs(UnmanagedType.Bool)]
X509StoreCtxInit( SafeX509StoreCtxHandle ctx, SafeX509StoreHandle store, SafeX509Handle x509, SafeX509StackHandle extraCerts)132         internal static extern bool X509StoreCtxInit(
133             SafeX509StoreCtxHandle ctx,
134             SafeX509StoreHandle store,
135             SafeX509Handle x509,
136             SafeX509StackHandle extraCerts);
137 
138         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509VerifyCert")]
X509VerifyCert(SafeX509StoreCtxHandle ctx)139         internal static extern int X509VerifyCert(SafeX509StoreCtxHandle ctx);
140 
141         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreCtxGetError")]
X509StoreCtxGetError(SafeX509StoreCtxHandle ctx)142         internal static extern X509VerifyStatusCode X509StoreCtxGetError(SafeX509StoreCtxHandle ctx);
143 
144         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreCtxGetErrorDepth")]
X509StoreCtxGetErrorDepth(SafeX509StoreCtxHandle ctx)145         internal static extern int X509StoreCtxGetErrorDepth(SafeX509StoreCtxHandle ctx);
146 
147         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509StoreCtxSetVerifyCallback")]
X509StoreCtxSetVerifyCallback(SafeX509StoreCtxHandle ctx, X509StoreVerifyCallback callback)148         internal static extern void X509StoreCtxSetVerifyCallback(SafeX509StoreCtxHandle ctx, X509StoreVerifyCallback callback);
149 
GetX509VerifyCertErrorString(X509VerifyStatusCode n)150         internal static string GetX509VerifyCertErrorString(X509VerifyStatusCode n)
151         {
152             return Marshal.PtrToStringAnsi(X509VerifyCertErrorString(n));
153         }
154 
155         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509VerifyCertErrorString")]
X509VerifyCertErrorString(X509VerifyStatusCode n)156         private static extern IntPtr X509VerifyCertErrorString(X509VerifyStatusCode n);
157 
158         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509CrlDestroy")]
X509CrlDestroy(IntPtr a)159         internal static extern void X509CrlDestroy(IntPtr a);
160 
161         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_PemWriteBioX509Crl")]
PemWriteBioX509Crl(SafeBioHandle bio, SafeX509CrlHandle crl)162         internal static extern int PemWriteBioX509Crl(SafeBioHandle bio, SafeX509CrlHandle crl);
163 
164         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_PemReadBioX509Crl")]
PemReadBioX509Crl(SafeBioHandle bio)165         internal static extern SafeX509CrlHandle PemReadBioX509Crl(SafeBioHandle bio);
166 
167         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509SubjectPublicKeyInfoDerSize")]
GetX509SubjectPublicKeyInfoDerSize(SafeX509Handle x509)168         internal static extern int GetX509SubjectPublicKeyInfoDerSize(SafeX509Handle x509);
169 
170         [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_EncodeX509SubjectPublicKeyInfo")]
EncodeX509SubjectPublicKeyInfo(SafeX509Handle x509, byte[] buf)171         internal static extern int EncodeX509SubjectPublicKeyInfo(SafeX509Handle x509, byte[] buf);
172 
173         internal enum X509VerifyStatusCode : int
174         {
175             X509_V_OK = 0,
176             X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT = 2,
177             X509_V_ERR_UNABLE_TO_GET_CRL = 3,
178             X509_V_ERR_UNABLE_TO_DECRYPT_CRL_SIGNATURE = 5,
179             X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY = 6,
180             X509_V_ERR_CERT_SIGNATURE_FAILURE = 7,
181             X509_V_ERR_CRL_SIGNATURE_FAILURE = 8,
182             X509_V_ERR_CERT_NOT_YET_VALID = 9,
183             X509_V_ERR_CERT_HAS_EXPIRED = 10,
184             X509_V_ERR_CRL_NOT_YET_VALID = 11,
185             X509_V_ERR_CRL_HAS_EXPIRED = 12,
186             X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD = 13,
187             X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD = 14,
188             X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD = 15,
189             X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD = 16,
190             X509_V_ERR_OUT_OF_MEM = 17,
191             X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT = 18,
192             X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN = 19,
193             X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY = 20,
194             X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE = 21,
195             X509_V_ERR_CERT_CHAIN_TOO_LONG = 22,
196             X509_V_ERR_CERT_REVOKED = 23,
197             X509_V_ERR_INVALID_CA = 24,
198             X509_V_ERR_PATH_LENGTH_EXCEEDED = 25,
199             X509_V_ERR_INVALID_PURPOSE = 26,
200             X509_V_ERR_CERT_UNTRUSTED = 27,
201             X509_V_ERR_CERT_REJECTED = 28,
202             X509_V_ERR_KEYUSAGE_NO_CERTSIGN = 32,
203             X509_V_ERR_UNABLE_TO_GET_CRL_ISSUER = 33,
204             X509_V_ERR_UNHANDLED_CRITICAL_EXTENSION = 34,
205             X509_V_ERR_KEYUSAGE_NO_CRL_SIGN = 35,
206             X509_V_ERR_UNHANDLED_CRITICAL_CRL_EXTENSION = 36,
207             X509_V_ERR_INVALID_NON_CA = 37,
208             X509_V_ERR_KEYUSAGE_NO_DIGITAL_SIGNATURE = 39,
209             X509_V_ERR_INVALID_EXTENSION = 41,
210             X509_V_ERR_INVALID_POLICY_EXTENSION = 42,
211             X509_V_ERR_NO_EXPLICIT_POLICY = 43,
212         }
213     }
214 }
215