As can get available templates from CA by name on .NET?

0

I have the desired result through utility the certutil:

PS C:\>> certutil -config "dev.root.ad\Dev Issuing CA" –Catemplates –v | select-string displayname

  displayName = DEMO AnyConnect 4 years
  displayName = ECS User

But on C# I have problems. This my code:

using CERTADMINLib;
using CERTCLILib;

namespace Services 
{
    public class CATemplates 
    {
        public const Int32 CrPropTemplates = 0x0000001D; // Configured Certificate Templates
        public const Int32 ProptypeString = 4;

        public static String GetCAPropertyDisplayName(string configString)
        {
            var request = new CCertRequest();

            //var templates = (String)request.GetCAProperty(configString, CrPropTemplates, 0, ProptypeString, 0);
            var displayName = request.GetCAPropertyDisplayName(configString, CrPropTemplates);

            return displayName;
        }
    }
}

I have COMException:

System.Runtime.InteropServices.COMException: 'CCertRequest::GetCAPropertyDisplayName: The permissions on this certification authority do not allow the current user to enroll for certificates. 0x80094011 (-2146877423 CERTSRV_E_ENROLL_DENIED)'

Through CCertAdmin I have same COMException.

I would like to find a solution without adding any permissions in local system and Domain. Do as well in the certutil. Magic certutil in parameter "-v"

c#
.net
asked on Stack Overflow Jan 17, 2020 by Vladimir K

1 Answer

0

This call:

var displayName = request.GetCAPropertyDisplayName(configString, CrPropTemplates);

is incorrect. ICertRequest::GetCAPropertyDisplayName gets display name of CA property, not the template. Commented line is correct one:

//var templates = (String)request.GetCAProperty(configString, CrPropTemplates, 0, ProptypeString, 0);

uncomment this line. You will get a string with OID and template common name on separate line. Split the string by \n character and take only lines that contain template name. Then query directory services to get the template object. They are stored at

"LDAP://CN={template name}, CN=Certificate Templates, CN=Public Key Services, CN=Services, {ConfigurationNamingContext}"

Configuration naming context is retrieved from LDAP://RootDSE. After getting template object from DS read displayName DS attribute to get display name of certificate template.

Update:

as for exception: make sure if caller has "Request Certificates" permission on CA server itself.

why certutil works in this context? It seems that it doesn't use ICertRequest::GetCAProperty method to retrieve templates and read them from Active Directory CA object (under Enrollment Services container). You may do the same. Read list of assigned templates from CA object and then read templates to get display name.

answered on Stack Overflow Jan 20, 2020 by Crypt32 • edited Jan 20, 2020 by Crypt32

User contributions licensed under CC BY-SA 3.0